I assume you want all this at compile time.
Here is a general explanation: tuple binding is similar to concatenating lists or arrays; the algorithm is the same. Here, given tuples a and b , I decided to move the last element of a to the beginning of b and repeat until a is empty.
First: basic structures. The following structure stores a package of parameters. It can be anything, for example a tuple:
template<typename... T> struct pack { static const unsigned int size = sizeof...(T); };
Please note that the packet size is stored inside it. This is not necessary, but it is convenient for explanation. Boost uses struct boost::tuples::length<T>::value (more verbose).
To access the element in the i-th position, we use a structure similar to boost::tuples::element<n, T> :
// Get i-th element of parameter pack // AKA 'implementation' // Principle: the element i is the first element of the sub-array starting at indice i-1 template<int n, typename F, typename... T> struct element_at : public element_at<n-1, T...> { }; template<typename F, typename... T> struct element_at<0, F, T...> { typedef F type; }; // Get i-th element of pack // AKA 'interface' for the 'pack' structure template<int n, typename P> struct element { }; template<int n, typename... T> struct element<n, pack<T...>> { typedef typename element_at<n, T...>::type type; };
Now we need to use a low-level operation that adds one element to the side of the package (adding left or right). Here the add on the left is selected, but this is not the only choice:
For templates, a does not change, and instead we use an index to find out which element to add. Inheritance defines a “type” of typedef, which is the concatenation of all indices after n and another tuple (not including n and in order). We just need to concatenate the element at index n on the left.
And this! Real-time example here .
Now, for the features of the set: you noticed that I did not use boost :: tuple or std :: tuple. This is due to the fact that many boost tuplesdo implementations do not have access to variational templates, therefore a fixed number of template parameters are used (they are equal to boost::tuples::null_type ). Including this directly in variable templates is a headache, so you need to have a different abstraction.
I also suggested that you can use C ++ 11 (with decltype in your question). Merging two tuples in C ++ 03 is possible, but more repetitive and boring.
You can easily convert pack to tuple: just change the definition of pack to:
template<typename... T> struct pack { static const unsigned int size = sizeof...(T); typedef boost::tuple<T...> to_tuple;