c++模板之SFINAE
什么是SFINAE?
Substitution failure is not an error,匹配失败并不是错误,意思是用函数模板匹配规则来判断类型的某个属性是否存在,也就是说SFINAE可以作为一种编译期的不完整内省方法
具体参见http://en.wikipedia.org/wiki/Substitution_failure_is_not_an_error
案例:
使用SFINAE判断模板参数是否是class(在很多场合这个trick非常有用):
template<typename T> class isClassA { typedef char _One; typedef struct{char a[2];}_Two; template<typename T> static _One isClass(int T::* p); template<typename T> static _Two isClass(...); public: static const int value=sizeof(isClass<T>(NULL))==sizeof(_One); };
使用SFINAE判断类是否有某个函数:
template<typename T> class HasFuncFoo { typedef char _One; typedef struct{char a[2];}_Two; template<typename T,void (T::*)()> struct FuncMatcher; template<typename T> static _One hasFunc(FuncMatcher<T,&T::fooFunc>*); template<typename T> static _Two hasFunc(...); public: static const int value=sizeof(hasFunc<T>(NULL))==sizeof(_One); };
如何根据自己的需要写SFINAE?
基本思路是想办法把要判断的东西放到函数参数中,比如上面的FuncMathcer就是很好的例子:把fooFunc作为一个模板类的模板参数,然后以这个类作为SFINAE函数的参数
SFINAE应用
1 tr1的enable_if用了很多SFIANE,遇到类似的场景可以考虑使用SFIANE
2 其他应用有待研究
ps.
看到一个很有意思的c++wikibook:http://en.wikibooks.org/wiki/More_C%2B%2B_Idioms,各种奇技淫巧