?? typetraits.h
字號:
// -*- C++ -*-
//##############################################################################
//The dnc Library
//Copyright (c) 2005 Dreamsoft 趙純華
//定義Type操作的基礎設施
//##############################################################################
//
//Last update: 2005-11-9
#ifndef __DNC_TYPETRAITS_H__
#define __DNC_TYPETRAITS_H__
/** If the compiler can implementation is_base<T> template,then has
* DNC_CANCHECKBASE define.
*/
#if !defined(__DMC__) && !defined(DNC_CANCHECKBASE)
#define DNC_CANCHECKBASE
#endif
namespace dnc{
/**
* 提供兩個尺寸不一樣的類型,用于sizeof操作符獲得不同的靜態(tài)整數
*/
typedef char yes_type;
struct no_type{
char padding[8];
};
/**
* 把整數或者一種類型轉換成另一種類型,把一個常數或者類型進行強化
* @code
* //根據整數重載函數
* void foo(int2type<0>){
* }
* void foo(int2type<1>){
* }
* //根據整數調用函數
* void test(){
* foo(int2type<0>()); //call foo(int2type<0>)
* foo(int2type<1>()); //call foo(int2type<1>)
* }
*
* //根據類型重載函數,但是不為類型創(chuàng)建對象
* void foo(type2type<MyType>){
* }
* void foo(type2type<int>){
* }
* //根據類型調用函數,但是不創(chuàng)建這個類型的對象
* void test(){
* foo(type2type<MyType>()); //call foo(type2type<MyType>);
* foo(type2type<int>()); //call foo(type2type<int>);
* }
* @endcode
*/
template <int v> struct int2type{enum { value = v };};
template <class T> struct type2type{typedef T OriginalType;};
/**
* 類型選擇器,相當于一個三元運算符
*/
template<bool flag>
struct selector_helper{
template<class T,class U>
struct select{
typedef T type;
};
};
template<>
struct selector_helper<false>{
template<class T,class U>
struct select{
typedef U type;
};
};
template <bool flag, typename T, typename U>
struct selector{
typedef typename selector_helper<flag>::template select<T,U>::type type;
};
/** cv_traits<T> const volatile traits.
* 多數compiler不能對const和volatile修飾進行模板特化,但是能對被const和
* volatile修飾的指針進行特化,這樣其實通過簡單的轉化就能處理任意的類型,所以
* 把這兩種情況放在一起處理.
* @param T any C++ type
* @return type 沒有經過const 和 volatile修飾的類型.
* @return is_const Bool value whether T is const.
* @return is_volatile Bool value whether T is volatile.
*/
template <typename T> struct cv_traits{};
template <typename T>
struct cv_traits<T*>{
enum{is_const = false,is_volatile = false};
typedef T type;
};
template <typename T>
struct cv_traits<const T*>{
enum{is_const = true,is_volatile = false};
typedef T type;
};
template <typename T>
struct cv_traits<volatile T*>{
enum{is_const = false,is_volatile = true};
typedef T type;
};
template <typename T>
struct cv_traits<const volatile T*>{
enum{is_const = true,is_volatile = true};
typedef T type;
};
//------------------------------------------------------------------------------
//判斷是否是數組類型
//------------------------------------------------------------------------------
#if 0
template< typename T > T(* is_array_tester1(type2type<T>) )(type2type<T>);
char is_array_tester1(...);
template< typename T> no_type is_array_tester2(T(*)(type2type<T>));
yes_type is_array_tester2(...);
template< typename T >
struct is_array
{
enum {
value =
sizeof(is_array_tester2(
is_array_tester1(
type2type<T>()
)
)) == 1
};
};
#else
template<class T> struct is_array{enum{value=false};};
template<class T> struct is_array<T[]>{enum{value=true};};
#ifndef __DMC__
template<class T,int C> struct is_array<T[C]>{enum{value=true};};
#endif
#endif
template <typename T> struct is_pointer{
enum{value=false};
};
template <typename T> struct is_pointer<T*>{
enum{value=true};
};
template <typename T> struct is_pointer<const T*>{
enum{value=true};
};
template <typename T> struct is_reference{
enum{value=false};
};
template <typename T> struct is_reference<T&>{
enum{value=true};
};
template <typename T> struct is_reference<const T&>{
enum{value=true};
};
/** template<class T> is_const;
*/
template <typename T> struct is_const{
enum{value=cv_traits<T>::is_const};
};
/** remove_reference<T>
*/
template<class T> struct remove_reference{
typedef T type;
};
template<class T> struct remove_reference<T&>{
typedef T type;
};
template<class T> struct remove_pointer{
typedef T type;
};
template<class T> struct remove_pointer<T*>{
typedef T type;
};
template <typename T, bool is_vol>
struct remove_const_helper{
typedef T type;
};
template <typename T>
struct remove_const_helper<T, true>{
typedef T volatile type;
};
template <typename T>
struct remove_const{
typedef typename cv_traits<T*>::type unqualified_type;
enum{is_volatile = cv_traits<T*>::is_volatile};
typedef typename remove_const_helper<
unqualified_type,is_volatile
>::type type;
};
//------------------------------------------------------------------------------
//is_integral 判斷是否是整數類型
//------------------------------------------------------------------------------
template<class T> struct is_integral{enum{value=false};};
template<> struct is_integral<unsigned char>{enum{value=true};};
template<> struct is_integral<unsigned short>{enum{value=true};};
template<> struct is_integral<unsigned int>{enum{value=true};};
template<> struct is_integral<unsigned long>{enum{value=true};};
#ifdef DNC_HASLONGLONG
template<> struct is_integral<unsigned long long>{enum{value=true};};
#endif
template<> struct is_integral<signed char>{enum{value=true};};
template<> struct is_integral<signed short>{enum{value=true};};
template<> struct is_integral<signed int>{enum{value=true};};
template<> struct is_integral<signed long>{enum{value=true};};
#ifdef DNC_HASLONGLONG
template<> struct is_integral<long long>{enum{value=true};};
#endif
template<> struct is_integral<bool>{enum{value=true};};
template<> struct is_integral<char>{enum{value=true};};
#ifdef DNC_HASWCHAR
template<> struct is_integral<wchar_t>{enum{value=true};};
#endif
//------------------------------------------------------------------------------
//is_float 判斷是否是浮點數類型
//------------------------------------------------------------------------------
template<class T> struct is_float{enum{value=false};};
template<> struct is_float<float>{enum{value=true};};
template<> struct is_float<double>{enum{value=true};};
template<> struct is_float<long double>{enum{value=true};};
//------------------------------------------------------------------------------
//判斷是否是算數類型
//------------------------------------------------------------------------------
template<class T> struct is_arithmetic
{enum{value=is_integral<T>::value||is_float<T>::value};};
//------------------------------------------------------------------------------
//判斷是否是void類型
//------------------------------------------------------------------------------
template<typename T> struct is_void{enum{value=false};};
template<> struct is_void<void> {enum{value=true};};
//------------------------------------------------------------------------------
//判斷是否是class或者union或者struct
//------------------------------------------------------------------------------
template <typename T>
struct is_class{
template <class U> static yes_type is_class_or_union_tester(void(U::*)(void));
template <class U> static no_type is_class_or_union_tester(...);
enum{value = sizeof(is_class_or_union_tester<T>(0)) == sizeof(yes_type)};
};
//------------------------------------------------------------------------------
//判斷From是否能轉換成To
//------------------------------------------------------------------------------
template <class From, class To>
struct is_convertible{
private:
static no_type is_convertible_tester(...);
static yes_type is_convertible_tester(To);
public:
enum{value = sizeof(is_convertible_tester(From())) == sizeof(yes_type)};
};
//------------------------------------------------------------------------------
//判斷T和U是否是同一種類型
//------------------------------------------------------------------------------
template <class T, class U>
struct is_same{
private:
static yes_type is_same_tester(T**, T**);
static no_type is_same_tester(...);
public:
enum{value =
sizeof(yes_type) == sizeof(is_same_tester((T**)0,(U**)0)) &&
sizeof(T) == sizeof(U)
};
};
//------------------------------------------------------------------------------
//判斷是否是枚舉類型
//------------------------------------------------------------------------------
template<bool flag,class T>
struct is_enum_helper{
static no_type is_enum_tester(...);
static yes_type is_enum_tester(int);
enum{value = sizeof(is_enum_tester(T())) == sizeof(yes_type)};
};
template<class T>
struct is_enum_helper<true,T>{
enum{value=false};
};
template<typename T>
struct is_enum{
enum{
value=is_enum_helper<
is_integral<T>::value||
is_float<T>::value||
is_void<T>::value||
is_array<T>::value||
is_class<T>::value||
is_pointer<T>::value||
is_reference<T>::value,T>::value
};
};
//------------------------------------------------------------------------------
//remove const and volatile modifier
//------------------------------------------------------------------------------
template<class T>
struct remove_cv{
typedef typename cv_traits<T*>::type type;
};
//------------------------------------------------------------------------------
//判斷B是否是D的基類
//------------------------------------------------------------------------------
#ifdef DNC_CANCHECKBASE
template <typename B, typename D>
struct bd_helper{
template <typename T>
static yes_type check(D const volatile *, T);
static no_type check(B const volatile *, int);
};
template<typename B, typename D>
struct is_base_impl2{
struct Host{
operator D const volatile *();
operator B const volatile *() const;
};
enum{value = sizeof(bd_helper<B,D>::check(Host(), 0)) ==
sizeof(yes_type)};
};
#else
//broken version
template<typename B, typename D>
struct is_base_impl2{
enum{value = is_convertible<D*,B*>::value};
};
#endif
template <typename B, typename D>
struct is_base_impl3{
enum{value = false};
};
template <bool ic1, bool ic2, bool iss>
struct is_base_select{
template <class T, class U>
struct rebind
{
typedef is_base_impl3<T,U> type;
};
};
template <>
struct is_base_select<true,true,false>{
template <class T, class U>
struct rebind
{
typedef is_base_impl2<T,U> type;
};
};
template <typename B, typename D>
struct is_base{
typedef typename cv_traits<B*>::type ncvB;
typedef typename cv_traits<D*>::type ncvD;
enum{
b_is_class = is_class<B>::value,
d_is_class = is_class<D>::value,
bd_is_same = is_same<B,D>::value
};
typedef is_base_select<
b_is_class,
d_is_class,
bd_is_same> binder_selector;
typedef typename binder_selector::template rebind<ncvB,ncvD> binder;
typedef typename binder::type bound_type;
enum{value = bound_type::value};
};
}
#endif //__DNC_TYPETRAITS_H__
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -