您的位置:首页 > 编程语言 > C语言/C++

使用c++11改写loki的TypeList

2014-02-16 15:24 274 查看
最近看了C++11的一些特性,最感兴趣的是可变模板参数,自动类型推断和匿名函数。

Loki中的TypeList,是需要递归定义的,并且需要一个NullType作为尾节点。

可变模板参数使得实现TypeList更简洁,更易懂。

以下是我用C++11实现TypeList,其实只用了可变模板参数。

去掉了递归定义,特别是尾节点可直接使用typelist<>,使得整个语义很美。

//////////////////////////////////////////////////////////
template<typename... TList>
struct typelist
{
};

typedef typelist<> nulllist;

//////////////////////////////////////////////////////////
template<typename... TList> struct length;

template<typename... TList>
struct length< typelist<TList...> >
{
enum { value = sizeof...(TList) };
};

//////////////////////////////////////////////////////////
template<typename T, typename... TList> struct push_front;

template<typename T, typename... TList>
struct push_front< T, typelist<TList...> >
{
typedef typelist<T, TList...>  type;
};

//////////////////////////////////////////////////////////
template<typename... TList> struct pop_front;

template<typename T, typename... TList>
struct pop_front< typelist<T, TList...> >
{
typedef typelist<TList...> type;
};

template<>
struct pop_front< nulllist >
{
typedef nulllist type;
};

//////////////////////////////////////////////////////////
template<unsigned int N, typename... TList> struct at;

template<unsigned int N, typename T, typename... TList>
struct at< N, typelist<T, TList...> >
{
typedef typename at< N-1, typelist<TList...> >::type type;
};

template<typename T, typename... TList>
struct at< 0, typelist<T, TList...> >
{
typedef T type;
};

template<>
struct at< 0, nulllist >
{
typedef nulllist type;
};

//////////////////////////////////////////////////////////
template<int A, int B>
struct IndexFixer
{
enum { value = (A == B) ? B : A + 1 };
};

//////////////////////////////////////////////////////////
template<typename T, typename... TList> struct indexof;

template<typename T, typename H, typename... TList>
struct indexof< T, typelist<H, TList...> >
{
enum { value = IndexFixer<indexof<T, typelist<TList...>>::value, -1>::value };
};

template<typename T, typename... TList>
struct indexof< T, typelist<T, TList...> >
{
enum { value = 0 };
};

template<typename T>
struct indexof< T, nulllist >
{
enum { value = -1 };
};

//////////////////////////////////////////////////////////
template<typename A, typename B> struct concat;

template<typename... A, typename... B>
struct concat<typelist<A...>, typelist<B...> >
{
typedef typelist<A..., B...> type;
};

template<typename T, typename... TList>
struct concat<typelist<TList...>, T >
{
typedef typelist<TList..., T> type;
};

template<typename T, typename... TList>
struct concat< T, typelist<TList...> >
{
typedef typelist<T, TList...>  type;
};

//////////////////////////////////////////////////////////
template<typename T, typename... TList> struct erase;

template<typename T, typename H, typename... TList>
struct erase<T, typelist<H, TList...> >
{
typedef typename concat<H, typename erase< T, typelist<TList...> >::type>::type type;
};

template<typename T, typename... TList>
struct erase<T, typelist<T, TList...> >
{
typedef typelist<TList...> type;
};

template<typename T>
struct erase<T, nulllist >
{
typedef nulllist type;
};

//////////////////////////////////////////////////////////
template<typename T, typename... TList> struct erase_all;

template<typename T, typename H, typename... TList>
struct erase_all<T, typelist<H, TList...> >
{
typedef typename concat<H, typename erase_all< T, typelist<TList...> >::type>::type type;
};

template<typename T, typename... TList>
struct erase_all<T, typelist<T, TList...> >
{
typedef typename erase_all< T,typelist<TList...> >::type type;
};

template<typename T>
struct erase_all<T, nulllist >
{
typedef nulllist type;
};

//////////////////////////////////////////////////////////
template<typename T, typename...TList> struct no_duplicate;

template<typename T, typename...TList>
struct no_duplicate< typelist<T, TList...> >
{
private:
typedef typename no_duplicate< typelist<TList...> >::type inner;
typedef typename erase<T, inner>::type inner_result;
public:
typedef typename concat<T, inner_result>::type type;
};

template<>
struct no_duplicate< nulllist >
{
typedef nulllist type;
};

//////////////////////////////////////////////////////////
template<typename R, typename T, typename...TList> struct replace;

template<typename R, typename T, typename H, typename...TList>
struct replace<R, T, typelist<H, TList...> >
{
typedef typename concat<H, typename replace<R, T, typelist<TList...>>::type>::type type;
};

template<typename R, typename H, typename...TList>
struct replace<R, H, typelist<H, TList...> >
{
typedef typename concat<R, typelist<TList...> >::type type;
};

template<typename R, typename T>
struct replace<R, T, nulllist >
{
typedef nulllist type;
};

//////////////////////////////////////////////////////////
template<typename R, typename T, typename...TList> struct replace_all;

template<typename R, typename T, typename H, typename...TList>
struct replace_all<R, T, typelist<H, TList...> >
{
typedef typename concat<H, typename replace_all<R, T, typelist<TList...>>::type>::type type;
};

template<typename R, typename H, typename...TList>
struct replace_all<R, H, typelist<H, TList...> >
{
typedef typename concat<R, typename replace_all<R, H, typelist<TList...>>::type >::type type;
};

template<typename R, typename T>
struct replace_all<R, T, nulllist >
{
typedef nulllist type;
};

//////////////////////////////////////////////////////////
template<typename T, typename...TList> struct reverse;

template<typename T, typename...TList>
struct reverse<typelist<T, TList...> >
{
typedef typename concat<typename reverse<typelist<TList...>>::type, T>::type type;
};

template<>
struct reverse< nulllist >
{
typedef nulllist type;
};


例子:

#include <iostream>
#include <vector>
#include "TypeList.h"
#include <type_traits>

int main()
{
typedef typelist<int, float, bool, float> testlist;
typedef typelist<float, bool> tlist;
typedef typelist<int, float> hlist;
typedef typelist<> elist;
typedef typelist<int> ilist;
typedef testlist mylist;

std::cout << "length: " << length<mylist>::value << std::endl;
bool b;
b = std::is_same<at<2, mylist>::type, bool>::value;
std::cout << "is same: " << b << std::endl;
b = std::is_same<push_front<int, elist>::type, ilist>::value;
std::cout << "is same: " << b << std::endl;
std::cout << "indexof : " << indexof<bool, mylist>::value << std::endl;
b = std::is_same<pop_front<typelist<>>::type, pop_front<ilist>::type>::value ;
std::cout << "is same: " << b << std::endl;
b = std::is_same< erase<bool, mylist>::type, typelist<int, float, float>>::value;
std::cout << "is same: " << b << std::endl;
b = std::is_same< no_duplicate<mylist>::type, typelist<int, float, bool>>::value;
std::cout << "is same: " << b << std::endl;
b = std::is_same< replace<double, bool, mylist>::type, typelist<int, float, double, float>>::value;
std::cout << "is same: " << b << std::endl;
b = std::is_same< replace_all<double, float, mylist>::type, typelist<int, double, bool, double>>::value;
std::cout << "is same: " << b << std::endl;
b = std::is_same< reverse<mylist>::type, typelist<float, bool, float, int>>::value;
std::cout << "is same: " << b << std::endl;

//std::cout << "is same: " << CompileTimeCount(int) << std::endl;
//std::cout << "is same: " << CompileTimeCount(int) << std::endl;
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: