使用 SFINAE 检测是否存在 void return 类型的函数
Using SFINAE to detect existence of a function of void return type
这是我的情况。我正在尝试检测某个类型是否具有 nlohmann::json、namley to_json
使用的特殊方法。现在我看到了以下使用 SFINAE 进行免费功能检查的解决方案:
Checking whether a function (not a method) exists in c++11 via templates
SFINAE: detect if class has free function
但这些方法至少似乎依赖于函数的 return 类型 是否无效。在 to_json
的情况下,签名如下:
void to_json(json& j, const T& p);
which returns void... 从而使这些方法失败(第二种方法实际上不起作用,因为为每种类型定义自定义包装器根本不可行)。
我修改了第一种方法,果然不出所料:
#include <iostream>
#include <type_traits>
#include "json.hpp"
template<class...> struct voider { using type = void; };
template<class... T> using void_t = typename voider<T...>::type;
template<class T, class = void>
struct is_jstreamable : std::false_type{};
template<class T>
struct is_jstreamable<T, void_t<decltype(to_json(std::declval<nlohmann::json &>(),
std::declval<T>()))>> : std::true_type {};
struct Foo;
template<typename T>
typename std::enable_if<is_jstreamable<T>::value,
void>::type
bar(){
std::cout << "It works!" << std::endl;
};
template<typename T>
typename std::enable_if<!is_jstreamable<T>::value,
void>::type
bar(){
std::cout << "It doesn't work!" << std::endl;
}
int main(){
//int does have conversion
bar<int>();
//foo does not have conversion
bar<Foo>();
}
它无法工作,因为它是 void 类型,控制台 returning:
It doesn't work!
It doesn't work!
而不是预期的
It works!
It doesn't work!
我看到了 determining if the return of a function is void 的方法,但我不确定如何将其合并为我的问题的解决方案
nlohmann::json 有多种方法可以将给定类型转换为 json。没有为 int
定义 to_json
,因此您的类型特征按指定工作。
相反,检测您是否可以将类型转换为 nlohmann::json
对象:
template <typename T>
using is_jstreamable = std::is_convertible<T, nlohmann::json>;
这是我的情况。我正在尝试检测某个类型是否具有 nlohmann::json、namley to_json
使用的特殊方法。现在我看到了以下使用 SFINAE 进行免费功能检查的解决方案:
Checking whether a function (not a method) exists in c++11 via templates
SFINAE: detect if class has free function
但这些方法至少似乎依赖于函数的 return 类型 是否无效。在 to_json
的情况下,签名如下:
void to_json(json& j, const T& p);
which returns void... 从而使这些方法失败(第二种方法实际上不起作用,因为为每种类型定义自定义包装器根本不可行)。
我修改了第一种方法,果然不出所料:
#include <iostream>
#include <type_traits>
#include "json.hpp"
template<class...> struct voider { using type = void; };
template<class... T> using void_t = typename voider<T...>::type;
template<class T, class = void>
struct is_jstreamable : std::false_type{};
template<class T>
struct is_jstreamable<T, void_t<decltype(to_json(std::declval<nlohmann::json &>(),
std::declval<T>()))>> : std::true_type {};
struct Foo;
template<typename T>
typename std::enable_if<is_jstreamable<T>::value,
void>::type
bar(){
std::cout << "It works!" << std::endl;
};
template<typename T>
typename std::enable_if<!is_jstreamable<T>::value,
void>::type
bar(){
std::cout << "It doesn't work!" << std::endl;
}
int main(){
//int does have conversion
bar<int>();
//foo does not have conversion
bar<Foo>();
}
它无法工作,因为它是 void 类型,控制台 returning:
It doesn't work!
It doesn't work!
而不是预期的
It works!
It doesn't work!
我看到了 determining if the return of a function is void 的方法,但我不确定如何将其合并为我的问题的解决方案
nlohmann::json 有多种方法可以将给定类型转换为 json。没有为 int
定义 to_json
,因此您的类型特征按指定工作。
相反,检测您是否可以将类型转换为 nlohmann::json
对象:
template <typename T>
using is_jstreamable = std::is_convertible<T, nlohmann::json>;