atomic 注释25:atomic<T>的父类 _Choose_atomic_base_t<T,T>或 _Choose_atomic_base2_t<T,T>及 atomic<T> 的继承关系总图

(67) 接着,经过前面很长的铺垫,那么多基础类。整数,浮点数,指针,引用,各种类型都可以成员原子量 atomic《T》 中的数据成员。现在开始学习 atomic《T》 的父类 _Choose_atomic_base_t《T , T》 或 _Choose_atomic_base2_t《T , T》。因为众多的数据类型,只接受各不相同的数学运算。所以 atomic 的父类也是千奇百怪。先学习 atomic《T》 的继承关系。再学习其代码:

template <class _Ty, _Ty _Val>
struct integral_constant {  static constexpr _Ty value = _Val;  }; // 类内声明的静态变量,必须为常量

template <bool _Val>
using bool_constant = integral_constant<bool, _Val>;

using true_type  = bool_constant<true > ;
using false_type = bool_constant<false> ;
//**********************************************************************************************
template <bool _First_value, class _First, class... _Rest> // handle true trait or last trait
struct _Disjunction {                                  // 泛化模板类
    using type = _First;
};

template <class _False, class _Next, class... _Rest>   // first trait is false, try the next trait
struct _Disjunction<false, _False, _Next, _Rest...> {  // 特化模板类
    using type = typename _Disjunction<_Next::value, _Next, _Rest...>::type;
};

template <class... _Traits>  // If _Traits is empty, false_type  泛化模板类,处理模板参数的数量为 0 的情形
struct disjunction : false_type {};       // disj 有一个为真就为 真,所有都为假才为假。

template <class _First, class... _Rest>   // the first true trait in _Traits, or the last trait if none are true
struct disjunction<_First, _Rest...> : _Disjunction<_First::value, _First, _Rest...>::type { }; // 特化模板类

template <class... _Traits>
bool disjunction_v = disjunction<_Traits...>::value;   // 类名::成员名,用双引号是对的,不要用句点。
//**********************************************************************************************
template <class _Ty, class... _Types> // true if and only if _Ty is in _Types
bool _Is_any_of_v = disjunction_v<is_same<_Ty, _Types>...>;

template <class _Ty>
bool is_floating_point_v = _Is_any_of_v<remove_cv_t<_Ty>, float, double, long double>;
//**********************************************************************************************
template <bool> 
struct _Select        {  template <class _Ty1, class>    using _Apply = _Ty1;  };

template <>
struct _Select<false> {  template <class, class _Ty2>    using _Apply = _Ty2;  };
//***********************************************************************************************
template <class _TVal, class _Ty = _TVal>   // 此处是为了区分浮点型与其它类型(整数、指针等)
using _Choose_atomic_base_t = typename _Select<is_floating_point_v<_TVal>> ::
                                 template _Apply<_Atomic_floating<_Ty>, _Choose_atomic_base2_t<_TVal, _Ty>>;

template <class _Ty>  // atomic value
struct atomic : _Choose_atomic_base_t<_Ty> {  } ; 

(68)接着学习 atomic《T》 的另一个父类 _Choose_atomic_base2_t《T , T》,适用于 T 非浮点数的情形

_Atomic_integral<T , 8> : _Atomic_storage<T , 8> ; // 特化版本之间,对应完成继承
_Atomic_integral<T , 4> : _Atomic_storage<T , 4> ;
_Atomic_integral<T , 2> : _Atomic_storage<T , 2> ;
_Atomic_integral<T , 1> : _Atomic_storage<T , 1> ;
//************************************************************************************************
template <class _Ty, size_t = sizeof(_Ty)> // 有 1 2 4 8 的重载, 也有其泛化版本的定义
struct _Atomic_storage {  };   

template <class _Ty, size_t = sizeof(_Ty)> // 有 1 2 4 8 的重载,但其泛化版本无定义
struct _Atomic_integral : _Atomic_storage<_Ty> {};

template <class _Ty>  // 本模板作为普通整形 atomic<int> 的父类 ,本类并无数据成员
struct _Atomic_integral_facade : _Atomic_integral<_Ty>{  };
//***************************************************************************************************
template <class _Ty>  // 注意,这里把  bool  类型也视为了 integral 整数类型。
bool is_integral_v = _Is_any_of_v < remove_cv_t<_Ty> , bool , char, signed char, unsigned char,
    wchar_t,
#ifdef __cpp_char8_t
    char8_t,
#endif // __cpp_char8_t
    char16_t, char32_t, short, unsigned short, int, unsigned int, long, unsigned long, long long, unsigned long long>;
//***************************************************************************************************
template <class _TVal, class _Ty = _TVal> // T为整数及其引用类型且非 bool时,atomic 的父类是 _Atomic_integral_facade<T>
using _Choose_atomic_base2_t =  typename _Select< is_integral_v<_TVal> && !is_same_v<bool, _TVal>> :: 
          template _Apply< _Atomic_integral_facade<_Ty> ,          // 然后对 bool 、指针类型的情况继续选择
        typename _Select<is_pointer_v<_TVal> && is_object_v<remove_pointer_t<_TVal>>>::  
    template _Apply< _Atomic_pointer<_Ty>, _Atomic_storage<_Ty>  > // 指针类型,也要确定不是指向函数与引用的指针。 
                               >;  // 最后只剩下 bool 类型,故 atomic<bool> 直接继承 _Atomic_storage<T> 的泛化版本。

(69) 接着继续展开 atomic《T》当 T 为 bool 类型或指针类型时候的泛型推导

template <class>
bool is_pointer_v = false; // determine whether _Ty is a pointer

template <class _Ty>
bool is_pointer_v<_Ty*> = true;

template <class _Ty>
bool is_pointer_v<_Ty* const> = true;

template <class _Ty>
bool is_pointer_v<_Ty* volatile> = true;

template <class _Ty>
bool is_pointer_v<_Ty* const volatile> = true;
//*****************************************************************************
template <class _Ty>
struct remove_pointer                     {    using type = _Ty;  };

template <class _Ty>
struct remove_pointer<_Ty*>               {    using type = _Ty;  };

template <class _Ty>
struct remove_pointer<_Ty* const>         {    using type = _Ty;  };

template <class _Ty>
struct remove_pointer<_Ty* volatile>      {    using type = _Ty;  };

template <class _Ty>
struct remove_pointer<_Ty* const volatile> {   using type = _Ty;  };

template <class _Ty>
using remove_pointer_t = typename remove_pointer<_Ty>::type;
//**************************************************************************************************
template <class _Ty> // only function types and reference types can't be const qualified
bool is_function_v =  !is_const_v<const _Ty> && !is_reference_v<_Ty>;

template <class _Ty>  // 对于函数和引用类型   is_const_v<const _Ty> = false ,这是编译器的特殊设置
struct is_function : bool_constant<is_function_v<_Ty>> {};

template <class _Ty> // only function types and reference types can't be const qualified
bool is_object_v =  is_const_v<const _Ty> && !is_void_v<_Ty>;

(70) 通过以上的分析,泛型推导,了解了一些关于 atomic《T》的父类的知识。当 T 为整数及其引用、 bool 、浮点、指针类型、或自定义类型时, atomic《T》 的父类是不同的,父类类型可以是这些:_Atomic_floating《T》、_Atomic_integral_facade《T》、_Atomic_pointer《T》、_Atomic_storage《T》(适用于大小非 1 2 4 8 16 的自定义类型数据)、_Atomic_storage《T , 1》(适用于 1 字节的 bool 类型 、char 类型以及 1 字节大小的自定义类型)

接着我们验证一下 atomic 类型的父类的类型

在这里插入图片描述

++ 测试结果如下:

在这里插入图片描述

(71)接着给出 atomic《T》 的 父子继承关系的总图,更有利于弄清记忆这些类的定义、功能与作用:

在这里插入图片描述

(72)

谢谢

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

zhangzhangkeji

谢谢支持

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值