diff options
author | Douglas Gregor <dgregor@apple.com> | 2009-06-09 21:22:32 +0000 |
---|---|---|
committer | Douglas Gregor <dgregor@apple.com> | 2009-06-09 21:22:32 +0000 |
commit | 6d968e89411406f0fd22ae69c77c79a425e2de6f (patch) | |
tree | 6f578c48d6ccf872d359baabb16d4e39d279dd3d | |
parent | d708c72e3e5186662fb0045d2bd666bfd93a013d (diff) |
Example metaprogram for reversing and searching in a type list
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@73147 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | test/SemaTemplate/example-typelist.cpp | 70 |
1 files changed, 70 insertions, 0 deletions
diff --git a/test/SemaTemplate/example-typelist.cpp b/test/SemaTemplate/example-typelist.cpp index e130725530..4a2aeb20e7 100644 --- a/test/SemaTemplate/example-typelist.cpp +++ b/test/SemaTemplate/example-typelist.cpp @@ -1,5 +1,6 @@ // RUN: clang-cc -fsyntax-only -verify %s +// A simple cons-style typelist struct nil { }; template<typename Head, typename Tail = nil> @@ -8,6 +9,17 @@ struct cons { typedef Tail tail; }; +// is_same trait, for testing +template<typename T, typename U> +struct is_same { + static const bool value = false; +}; + +template<typename T> +struct is_same<T, T> { + static const bool value = true; +}; + // metaprogram that computes the length of a list template<typename T> struct length; @@ -26,3 +38,61 @@ typedef cons<unsigned char, cons<unsigned int, cons<unsigned long> > > > unsigned_inttypes; int length0[length<unsigned_inttypes>::value == 4? 1 : -1]; + +// metaprogram that reverses a list + +// FIXME: I would prefer that this be a partial specialization, but +// that requires partial ordering of class template partial +// specializations. +template<typename T> +class reverse { + typedef typename reverse<typename T::tail>::type reversed_tail; + + typedef typename reverse<typename reversed_tail::tail>::type most_of_tail; + +public: + typedef cons<typename reversed_tail::head, + typename reverse<cons<typename T::head, most_of_tail> >::type> type; +}; + +template<typename Head> +class reverse<cons<Head> > { +public: + typedef cons<Head> type; +}; + +template<> +class reverse<nil> { +public: + typedef nil type; +}; + +int reverse0[is_same<reverse<unsigned_inttypes>::type, + cons<unsigned long, + cons<unsigned int, + cons<unsigned short, + cons<unsigned char> > > > >::value? 1 : -1]; + +// metaprogram that finds a type within a list + +// FIXME: I would prefer that this be a partial specialization, but +// that requires partial ordering of class template partial +// specializations. +template<typename List, typename T> +struct find : find<typename List::tail, T> { }; + +template<typename Tail, typename T> +struct find<cons<T, Tail>, T> { + typedef cons<T, Tail> type; +}; + +template<typename T> +struct find<nil, T> { + typedef nil type; +}; + +int find0[is_same<find<unsigned_inttypes, unsigned int>::type, + cons<unsigned int, cons<unsigned long> > >::value? + 1 : -1]; +int find1[is_same<find<unsigned_inttypes, int>::type, nil>::value? 1 : -1]; + |