下面将介绍泛型编程最重要组件他们是:
1编译期断言
2编译期转换检测
3编译期选择
4编译期多态
5代码容器 再次说这是泛型里最重要组件值得你去理解和使用他们实现有很多版本Boost和Loki都有实现在认真比较以后我认为Loki确实更加简单和强大所以我选择Loki代码进行举例如果你有兴趣深入了解请读C设计新思维
值得注意是为了便于理解我把Loki代码进行了适当修改
1编译期断言
实现:
template<> struct CompileTimeError;
template<> struct CompileTimeError {};
# STATIC_CHECK(expr, msg) \\
{ CompileTimeError<((expr) != 0)> ERROR_##msg; (void)ERROR_##msg; }
原理:
利用template<> struct CompileTimeError
使用:
const i = 0;
STATIC_CHECK(i0, \"i因该等于0\");
2编译期转换检测
实现:
template < T, U>
struct ConversionHelper
{
typedef char Small;
struct Big { char dummy[2]; };
Big Test(...);
Small Test(U);
T MakeT;
};
template < T, U>
struct Conversion
{
typedef ConversionHelper
enum { exists = (typename H::Small) (H::Test(H::MakeT)) };
enum { exists2Way = exists && Conversion::exists };
enum { sameType = false };
};
template < T>
struct Conversion
{
enum { exists = 1, exists2Way = 1,sameType = 1 };
};
template < T>
struct Conversion
{
enum { exists = 1, exists2Way = 0,sameType = 0 };
};
template < T>
struct Conversion
{
enum { exists = 1, exists2Way = 0,sameType = 0 };
};
template <>
Conversion
{
public:
enum { exists = 1, exists2Way = 1,sameType = 1 };
};
# SUPERSUBCLASS(T, U) \\
(Conversion
!Conversion
# SUPERSUBCLASS_STRICT(T, U) \\
(SUPERSUBCLASS(T, U) && \\
!Conversion
原理:
利用参数列表型别推测机制得到编译器使用哪个而返回型别接着利用 定会在编译期求出值来获得返回型别大小依此来判断了哪个然后在利用enum是编译期确定常数把返回值具体化出来
使用:
A { };
B : public A { };
STATIC_CHECK( SUPERSUBCLASS(A, B), \"A因该是B基类\");
3编译期选择
实现:
template
struct Select
{
typedef T Result;
};
template
struct Select
{
typedef U Result;
};
原理:
模板偏特化
使用:
A { };
B { };
template
C : public Select { };
4编译期多态
实现:
template< T>
Relex
{
private:
Relex(const Relex&);
Relex& operator = (const Relex&);
public:
typedef T _HostType;
typedef T& _HostReference;
typedef T* _HostPoer;
public:
Relex { }
T* GetHostPtr { reerpret_cast
};
原理:
模板迭代编译
使用:
template< T>
struct A : Relex
{
void func1 { GetHostPtr->func2; }
};
template< T>
struct B : Relex
{
void func2 { GetHostPtr->func1; }
};
template> T1, template<> T2>
C_Impl : public T1
typedef C_Impl C;
5代码容器
这里实现非常巨大就不写了你可以自己去看代码
实现:
template < T, U>
struct Typelist //请想想STL里list非常象这里Tail又是个Typelist这样形成个链
{
typedef T Head;
typedef U Tail;
};
//Typelist头是Typelist
struct NullType { };
struct EmptyType { };
//下面是操作Typelist类
template < TList> struct Length;
template < TList, unsigned index> struct TypeAt;
template < TList, unsigned index,typename DefaultType = NullType> struct TypeAtNonStrict;
template < TList, T> struct IndexOf;
template < TList, T> struct Append;
template < TList, T> struct Erase;
template < TList, T> struct EraseAll;
template < TList> struct NoDuplicates;
template < TList, T, U> struct Replace;
template < TList, T, U> struct ReplaceAll;
template < TList> struct Reverse;
template < TList, T> struct MostDerived;
template < TList> struct DerivedToFront;
//下面就是代码容器典型模板递归和模板偏特化运用请仔细看其实很简单
template < TList, template <> Unit>
GenScatterHierarchy;
template < T1, T2, template <> Unit>
GenScatterHierarchy
: public GenScatterHierarchy
, public GenScatterHierarchy
{
public:
typedef Typelist
typedef GenScatterHierarchy
typedef GenScatterHierarchy
template
{
typedef Unit
};
};
template < AtomicType, template <> Unit>
GenScatterHierarchy : public Unit
{
typedef Unit LeftBase;
template
{
typedef Unit
};
};
template > Unit>
GenScatterHierarchy
{
template
{
typedef Unit
};
};
template
<
TList,
template < AtomicType, Base> Unit,
Root = EmptyType
>
GenLinearHierarchy;
template
<
T1,
T2,
template <, > Unit,
Root
>
GenLinearHierarchy
: public Unit< T1, GenLinearHierarchy
template
<
T,
template <, > Unit,
Root
>
GenLinearHierarchy
: public Unit
template < i, H>
typename FieldHelper
原理:
metaprogram也就是模板递归模板偏特化
使用:
使用Loki里提供宏Loki提供了50个宏
运用1实现Tuple:
template < T>
struct TupleUnit
{
T value_;
operator T& { value_; }
operator const T& const { value_; }
};
template < TList>
struct Tuple : public GenScatterHierarchy
A { };
B { };
C { };
D { };
typedef Tuple
TupleClass obj;
B& b = Field<1>(obj);
运用2实现个抽象工厂:
Noir_Impl
{
template< P>
struct CAF_Product { P* Create_Impl { P; } };
template< CProductList>
CAF_AbstractFactory : public Loki::GenScatterHierarchy< CProductList, CAF_Product > { };
};
template< IProductList, CProductList>
struct Simple_AbstractFactory : public IProductList, private Noir_Impl::CAF_AbstractFactory< CProductList >
{
template< IP> IP* Create
{
typedef TypeAt< CProductList, IndexOf< IProductList, IP >::value > CP;
CP::Create_Impl;
}
};
IA { };
IB { };
IC { };
ID { };
A : public IA { };
B : public IB { };
C : public IC { };
D : public ID { };
typedef Simple_AbstractFactory< TYPELIST_4(IA, IB, IC, ID), TYPELIST_4(A, B, C, D) > MyAF;
MyAf factory;
IA* pA = factory.Create
IB* pB = factory.Create
IC* pC = factory.Create
ID* pD = factory.Create
最新评论