C++标准库 _Unwrappable

编译器: MSVC v142
所属文件: xutility
位置(行): 259
函数名称: _Unwrappable
函数描述:
_Unwrappable函数的作用是检查T是否同时具有_Unwrapped_Seek_to函数, 以及确保_Unwrapped可以作为参数传递给_Seek_to. 如果两个条件都满足, 那么它就是一个 _Unwrappable 对象, 即: 是一个迭代器.

源码:

// FUNCTION TEMPLATE _Get_unwrapped
template 
struct _Unwrappable : false_type {};

template 
struct _Unwrappable<_Iter, void_t()._Seek_to(_STD declval()._Unwrapped()))>>
    : _Allow_inheriting_unwrap<_Iter>::type {};

 

模板匹配

void_t()._Seek_to(_STD declval()._Unwrapped())), 又长又臭的过滤条件.

C++ 对待模板的套路就是利用 SFINAE 的失败不会退出编译而是跳过当前匹配的原则, 也就是说如果当前函数匹配过程出现任何失败, 就表示这个T不是一个Iterator对象.

void_t不管你返回的是什么类型,反正它永远都是void, 它就是一个垃圾箱, 用它只是因为它提供了接受任何类型参数, 正好可以利用这个机制把尖角括号内部的表达式消化掉, 出错就跳过当前匹配,不出错就表示第二个模板参数是一个void.

decltypedeclval搭配起来就是我可以不用实例化这个对象就可以检查这个对象的某个方法返回的是什么类型(备注: 不执行函数), 这里使用它们这个组合有两个目的, 一是检查这个T是否有_Seek_to方法和_Unwrapped方法, 二是检查_Seek_to的参数要求的类型跟_Unwrapped返回的类型是否对的上. 这两步检查任何一个步骤出错,_Unwrappable函数就认为T不是一个Iterator.

TODO: 为什么这里要检查两个成员函数, 直接检查_Unwrapped函数不就完事了吗?

 

继承

_Unwrappable 继承了 _Allow_inheriting_unwrap<_Iter>::type, 继承过程中又再做了一层筛选, 主要是证明Iterator的类别一致, 即证明你就是你.

template 
struct _Allow_inheriting_unwrap : true_type {};

template 
struct _Allow_inheriting_unwrap<_Iter, enable_if_t>>
    : false_type {};

你可能感兴趣的:(C++标准库 _Unwrappable)