假设以下相当简单的类:
struct A {
bool toBool() const { return true; }
template<typename T> T to() const { return T();}
};
现在,我想测试是否存在toBool
:
template<typename From, typename To>
class has_toBool_func
{
typedef char (&Two)[2];
template<typename F, bool (F::*)() const> struct helper {};
template<typename F> static char test(helper<F, &F::toBool>*);
template<typename F> static Two test(...);
public:
static const bool value = (sizeof(test<From>(0)) == sizeof(char));
};
定义和使用:
::std::cout << "int: " << has_toBool_func<int, bool>::value
<< ", A: " << has_toBool_func<A, bool>::value << ::std::endl;
并且只产生预期的输出“int:0,A:1”。
为函数模板尝试同样的事情:
class has_to_func
{
typedef char (&Two)[2];
template<typename F, To (F::*)() const> struct helper {};
template<typename F> static char test(helper<F, &F::to<To> >*);
template<typename F> static Two test(...);
public:
static const bool value = (sizeof(test<From>(0)) == sizeof(char));
};
::std::cout << "int: " << has_to_func<int, bool>::value
<< ", A: " << has_to_func<A, bool>::value << ::std::endl;
不会产生预期的输出“int:0,A:1”,而是编译错误。
为什么会这样?当然:我该如何解决它?
MSVC 2012
发出警告
warning C4346: 'F::to' : dependent name is not a type
prefix with 'typename' to indicate a type
see reference to class template instantiation 'xtd::has_to_func<From,To>' being compiled
这是没用的,因为依赖名称实际上不是类型和错误
error C2998: 'char test' : cannot be a template definition
这也不是很有帮助......
国际商会 13.0
首先给出错误
error : type name is not allowed
template<typename F> static char test(helper<F, &F::to<To>() >*);
(<To>
已标记)
它描述了问题,但仍然让我完全不知道为什么会发生这种情况以及另一个错误
error : expected a ")"
template<typename F> static char test(helper<F, &F::to<To>() >*);
(最后一个>
被标记)
我很确定这完全是胡说八道,只是因为编译器感到困惑才显示出来。