Loki::Typelistタイプリストは、以下の2つのクラスを使つて構成できる、型のリストである。
class NullType {};
template <typename H, typename T>
struct Typelist {
typedef H Head;
typedef T Tail;
};
タイプリストを作るには、以下の様にする。
typedef Typelist<char,
Typelist<unsigned char,
Typelist<signed char,
NullType> > > charlist;
これだと面倒臭いし可読性も悪いので、TYPELIST_X マクロが用意されてゐる。
#define TYPELIST_1(T1) ::Loki::Typelist<T1, ::Loki::NullType> #define TYPELIST_2(T1, T2) ::Loki::Typelist<T1, TYPELIST_1(T2) > ...
このマクロを使ふと、上述の charlist は次の様に書ける。
typedef TYPELIST_3(char, unsigned char, signed char) charlist;
タイプリストに対して、要素が値である普通のリストと同じ様に、様々な操作を定義することが出来る。
例へば、タイプリストの長さを得るテンプレートクラス Length は次の様にすれば良い。
template <typename List>
struct Length;
template <typename H, typename T>
struct Length<TypeList<H, T> > {
enum { value = Length<T>::value + 1 };
};
template <>
struct Length<NullType> {
enum { value = 0 };
};
tlist がタイプリストである時、Length<tlist>::value が tlist の長さを表す。tlist がタイプリストでない時はコンパイルエラーになる。
数値だけでなく、型を得る操作も定義出来る。例へば、N 番目の要素を得るには以下の様にする。
template <typename List, int N>
struct TypeAt;
template <typename H, typename T, int N>
struct TypeAt<TypeList<H, T>, N> {
typedef typename TypeAt<T, N-1>::Result Result;
};
template <typename H, typename T>
struct TypeAt<TypeList<H, T>, 0> {
typedef H Result;
};
TypeAt<tlist, 3>::Result とすれば、tlist の3番目の要素を得ることが出来る。
loki の typelist.h 内には、これらの他にもタイプリストを操作する様々なテンプレートが定義されてゐる。