i want write simple adder (for giggles) adds every argument , returns sum appropriate type. currently, i've got this:
#include <iostream> using namespace std; template <class t> t sum(const t& in) { return in; } template <class t, class... p> auto sum(const t& t, const p&... p) -> decltype(t + sum(p...)) { return t + sum(p...); } int main() { cout << sum(5, 10.0, 22.2) << endl; } on gcc 4.5.1 seems work fine 2 arguments e.g. sum(2, 5.5) returns 7.5. however, more arguments this, errors sum() not defined yet. if declare sum() however:
template <class t, class p...> t sum(const t& t, const p&... p); then works number of arguments, sum(2, 5.5) return integer 7, not expect. more 2 arguments assume decltype() have sort of recursion able deduce type of t + sum(p...). legal c++0x? or decltype() work non-variadic declarations? if case, how write such function?
i think problem variadic function template considered declared after specified return type sum in decltype can never refer variadic function template itself. i'm not sure whether gcc bug or c++0x doesn't allow this. guess c++0x doesn't allow "recursive" call in ->decltype(expr) part.
as workaround can avoid "recursive" call in ->decltype(expr) custom traits class:
#include <iostream> #include <type_traits> using namespace std; template<class t> typename std::add_rvalue_reference<t>::type val(); template<class t> struct id{typedef t type;}; template<class t, class... p> struct sum_type; template<class t> struct sum_type<t> : id<t> {}; template<class t, class u, class... p> struct sum_type<t,u,p...> : sum_type< decltype( val<const t&>() + val<const u&>() ), p... > {}; this way, can replace decltype in program typename sum_type<t,p...>::type , compile.
edit: since returns decltype((a+b)+c) instead of decltype(a+(b+c)) closer how use addition, replace last specialization this:
template<class t, class u, class... p> struct sum_type<t,u,p...> : id<decltype( val<t>() + val<typename sum_type<u,p...>::type>() )>{};
Comments
Post a Comment