#include
#include
//第二章已讨论过的一些函数,现在拿来使用
template
struct SSelect { typedef T Type; };
template
struct SSelect { typedef U Type; };
template
class CConversion
{
typedef char Small;
class CBig { char aBuff[2]; };
static Small Fun(U);
static CBig Fun(...);
static T MakeT();
public:
enum { eExists = sizeof(Fun(MakeT())) == sizeof(Small) };
enum { eExistsToWay = eExists && CConversion::eExists };
enum { eSameType = false };
};
template
class CConversion
{
public:
enum { eExists = true, eExistsToWay = true, eSameType = true };
};
template
struct IntToType
{
enum { eValue = nValue };
};
//核心代码
struct SNullType; //不进行实现,充当类型终止符
template
struct STypeList
{
typedef T Type_Head;
typedef U Type_Tail;
};
//别名定义
#define STYPELIST_1(T1) STypeList
#define STYPELIST_2(T1, T2) STypeList
#define STYPELIST_3(T1, T2, T3) STypeList
#define STYPELIST_4(T1, T2, T3, T4) STypeList
//... 可以无限延伸
//#define STYPELIST_100(...)
//长度运算
template struct SLength;
template<> struct SLength { enum { nLength = 0}; };
template struct SLength< STypeList >
{
enum { nLength = 1 + SLength::nLength }; //将自动递归展开
};
//类似索引访问
template struct STypeAt;
//偏特化前要进行声明,且不进行定义则当访问越界时编译会失败
template
struct STypeAt< STypeList, 0>
{
typedef T Result;
};
template
struct STypeAt, nId>
{
typedef typename STypeAt::Result Result;//将自动展开递归
};
//STypeAt模板类的展开是在编译器完成的,不会影响运行效率
//类型查找
template struct SFind;
template
struct SFind
{
enum { nId = -1 }; //被查找的类型不在类型列表中
};
template
struct SFind, U>
{
enum { nId = 0 };
};
template
struct SFind, U>
{
private:
enum { nTem = SFind::nId }; //将自动展开递归
public:
enum { nId = nTem == -1 ? -1 : 1 + nTem };
};
//附加元素
template struct SAppend;
template<> struct SAppend
{
typedef SNullType Type_NewType;
};
template struct SAppend
{
typedef STYPELIST_1(U) Type_NewType;
};
template
struct SAppend>
{
typedef STypeList Type_NewType;
};
template
struct SAppend, U>
{
typedef STypeList::Type_NewType>
Type_NewType; //愉快的自动展开递归
};
//移除元素
template struct SErase;
template
struct SErase
{
typedef SNullType Type_NewType;
};
template
struct SErase, T>
{
typedef T_Tail Type_NewType;
};
template
struct SErase, T>
{
typedef STypeList::Type_NewType>
Type_NewType;
};
//移除某个类型的全部元素
template struct SEraseAll;
template
struct SEraseAll
{
typedef SNullType Type_NewType;
};
template
struct SEraseAll, T>
{
//和SErase唯一的区别:发现符合条件项后并不停止,而是继续查找
typedef typename SEraseAll::Type_NewType Type_NewType;
};
template
struct SEraseAll, T>
{
typedef STypeList::Type_NewType>
Type_NewType;
};
//去重
template struct SNoDumplicate;
template<> struct SNoDumplicate
{
typedef SNullType Type_NewType;
};
template
struct SNoDumplicate>
{
private:
typedef typename SNoDumplicate::Type_NewType T0;
typedef typename SErase::Type_NewType T1;
public:
typedef STypeList Type_NewType;
};
//替换首个匹配类型
template struct SReplace;
template
struct SReplace
{
typedef SNullType Type_NewType;
};
template
struct SReplace, T, U>
{
typedef STypeList Type_NewType;
};
template
struct SReplace, T, U>
{
typedef STypeList
::Type_NewType> Type_NewType;
};
//替换全部匹配类型 书上没有,自己编的
template struct SReplaceAll;
template
struct SReplaceAll
{
typedef SNullType Type_NewType;
};
template
struct SReplaceAll, T, U>
{
typedef typename SReplaceAll, T, U>::Type_NewType
Type_NewType;
};
template
struct SReplaceAll, T, U>
{
typedef STypeList
::Type_NewType> Type_NewType;
};
//类型局部更改次序
template struct SMostDerived;
template struct SMostDerived
{
typedef T Type_NewType;
};
template
struct SMostDerived, T>
{
private:
typedef typename SMostDerived::Type_NewType TCandidate;
public:
typedef typename SSelect::eExists,
T_Head, TCandidate>::Type Type_NewType;
/*
typedef typename SSelect::eExists,
T_Head, TCandidate>::Type Type_NewType 的意思:
结论一:
TCandidate 是 T_Head 的派生类吗,
若是,则T_Head是父类,则Type_NewType = T_Head
若否,则Type_NewType = TCandidate本身
结论二:
TCandidate本身是一个递归,由结论一可知:
TCandidate是T_Tail中T类型的最底层基类或者是T类型本身
由上推知Type_NewType就是类型T的最底层基类类型
*/
};
template struct SDerivedToFront;
template<> struct SDerivedToFront
{
typedef SNullType Type_NewType;
};
template
struct SDerivedToFront>
{
private:
typedef typename SMostDerived::Type_NewType T_Tem0;
typedef typename SReplace::Type_NewType
T_Tem1;
public:
typedef typename STypeList Type_NewType;
};
class CF {};
class CC : public CF {};
class CCC : public CC {};
//产生散乱的继承体系
template class CUnit> class CTest;
template class CUnit>
class CTest, CUnit> :
public CTest, public CTest
{
public:
CTest()
{
printf("%s\n", typeid(STypeList).name());
}
};
template class CUnit> class CTest :
public CUnit
{
public:
CTest()
{
printf("%s\n", typeid(T).name());
}
};
template class CUnit> class CTest
{
public:
CTest(){printf("SNullType\n");}
};
template class CUnit>
CUnit& Field(CTest& Test)
{
//CUnit是CTest 的父类,这里是父类的引用接收派生类的对象
//当TList存在2个相同类型的时候,此转换函数就不好用了
return Test;
}
template class CUnit>
CUnit& FieldHelper(CTest& Test,
IntToType<0>)
{
CTest& Tem = Test;
return Tem;
}
template class CUnit>
CUnit::Result>& FieldHelper(CTest& Test, IntToType)
{
CTest& Tem = Test;
return FieldHelper(Tem, IntToType());
}
template class CUnit>
CUnit::Result>& Field
(CTest& Test)
{
return FieldHelper(Test, IntToType());
}
template class CUnit>//自己编的
typename STypeAt::Result & MyGet(CTest& Test)
{
return FieldHelper(Test, IntToType()).tValue;//结合 SValue 使用
}
template struct SValue
{
T tValue;
protected:
~SValue(){}
};
//产生线性继承体系
template class CUnit,
typename TRoot = SNullType>
class CLineCreate;
template class CUnit, typename TRoot>
class CLineCreate, CUnit, TRoot> :
public CUnit>
{
};
template class CUnit,
typename TRoot>
class CLineCreate : public CUnit
{
};
template
class CData
{
public:
virtual void Fun() {}
virtual ~CData() {}
};
template
class CData1 : public TBase
{
public:
virtual void Fun() {}
};
class CBase
{
public:
virtual ~CBase(){}
};
int main()
{
const char* aStr0[] =
{
typeid(STYPELIST_3(int, double, float)::Type_Head).name(),
//"int"
typeid(STYPELIST_2(int, double)::Type_Tail::Type_Head).name(),
//"double"
typeid(STypeAt::Result).name()
//"float"
};
//typeid(STypeAt::Result).name();
//error C2027: 使用了未定义类型“STypeAt”
int nLen = SLength::nLength;
//nLen = 4
int aId[] =
{
SFind::nId, //0
SFind::nId,//1
SFind::nId, //2
SFind::nId, //-1
};
const char* aStr1[] =
{
typeid(SAppend::Type_NewType).name(),
//"struct SNullType"
typeid(SAppend::Type_NewType).name(),
//"struct STypeList"
typeid(SAppend::Type_NewType).name()
//"struct STypeList >"
};
//元素全为true
bool aRe[] =
{
typeid(SAppend::Type_NewType)
== typeid(STYPELIST_3(int, double, char)),
typeid(SErase
::Type_NewType) == typeid(STYPELIST_3(int, char, double)),
typeid(SEraseAll::
Type_NewType) == typeid(STYPELIST_2(int, char)),
typeid(SNoDumplicate::
Type_NewType) == typeid(STYPELIST_3(int, double, char)),
typeid(SReplace::Type_NewType) == typeid(STYPELIST_4(int, long, char,
double)),
typeid(SReplaceAll::Type_NewType) == typeid(STYPELIST_4(int, long, char,
long))
};
const char* pStr = typeid
(SMostDerived::Type_NewType).name();
//"class CF"
bool nRe = typeid(SDerivedToFront
::Type_NewType) == typeid(STYPELIST_4(CF, CC, CCC, CF));
//nRe = true
CTest Test;
/*
输出:
int
bool
double
SNullType
struct STypeList
struct STypeList>
struct STypeList>>
*/
/*
Test对象的继承的基类:
SValue
SValue
SValue
CTest
CTest
CTest
CTest
CTest,SValue>
CTest>,SValue>
*/
(static_cast&>(Test)).tValue = 0;
(static_cast&>(Test)).tValue = 0.1;
Field(Test).tValue = true;
CTest Test1;
//warning C4584: “CTest”:
// 基类“CTest”已是“CTest”的基类
//Field(Test1).tValue = 1;
//error C2594: “return”: 从“CTest”到“SValue &”的转换不明确
Field<1>(Test1).tValue = 1; //第二个int成功被置为1
//自己实现tuple
CTest Test2;
MyGet<0>(Test2) = 1;
MyGet<1>(Test2) = 2;
MyGet<2>(Test2) = 1.1;
MyGet<3>(Test2) = true;
//Test2 中对应值均正确
CTest Data;
int nSize = sizeof Data; //nSize = 12 虚函数导致的开销 Win32环境
//Data对象的基类中的CData,CData,CData具有虚函数
CLineCreate Data1;
int nSize1 = sizeof Data1; //nSize1 = 4
/*
Data1对象的继承基类
CData1
CLineCreate,CData1,CBase>
CData1,CData1,CBase> >
CLineCreate >,CData1,CBase>
CData1 >,
CData1,CBase> >
*/
return 0;
}