Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using template class from template class in template method

I need to use a template class which is defined in another template class as parameter of another template as return value in template method. I know it sounds complicated, code below explains it better. Problem is that the code cannot be compiled, it ends with following error:

type/value mismatch at argument 2 in template parameter list for 'template<class T, template<class> class Policy> class Result'
expected a class template, got 'CDummy<T2>::Policy2'

but I'm pretty sure that given class fulfills needs. Problem is that the method, which uses it, is template too and so compiler does not know what exactly CDummy<T2>::Policy2 is. If the Policy2 would not be template, but regular class or if I could fill its argument, I would use typename which would tell the compiler not to worry about it, but how can this be done with template?

// I cannot change this interface - it's given by a library
template <class T, template <class> class Policy>
class Result : public Policy<T>
{
    T data;
};

template <class T>
class Policy1
{

};

// I use this for allowing Policy2 to change behaviour according Dummy
// while it keeps template interface for class above
template <class Dummy>
class CDummy
{
public:
    template <class T>
    class Policy2 : public Policy1<T>
    {

    };
};

// Both variables are created ok
Result<int, Policy1 > var1;
Result<int, CDummy<float>::Policy2 > var2;

// This is ok, too
template <class T>
Result<T, Policy1 > calc1()
{
    return Result<int, Policy1>();
}

// But this ends with the error:
// type/value mismatch at argument 2 in template parameter list for 'template<class T, template<class> class Policy> class Result'
// expected a class template, got 'CDummy<T2>::Policy2'
template <class T1, class T2>
Result<T1, CDummy<T2>::Policy2 > calc2() // <-- Here is the generated error
{
    typedef typename DummyTypedef CDummy<T2>;
    return Result<T1, DummyTypedef::Policy2>();
}

Notes:

  • I use gcc 4.7.3 32bit in GNU/Linux Ubuntu 13.04. 32 bit.
  • For various reasons, I cannot use C++11 standard (yet) and so I cannot use template typedefs

1 Answers

I believe that the name CDummy<T2>::Policy2 is a dependent name in that context and that you should use the template keyword to inform the compiler that it is indeed a template.

template <class T1, class T2>
Result<T1, CDummy<T2>::template Policy2 > calc2() // <-- Here is the generated error
//                     ^^^^^^^^

additionally the implementation of that same function seems to be wrong also. The order of typedefs is original name, new name, and CDummy<T2> is known to be a type (i.e. there is no need for the typename):

typedef CDummy<T2> DummyTypedef;

The return statement would then be:

return Result<T1, DummyTypedef::template Policy2>();
like image 63
David Rodríguez - dribeas Avatar answered Dec 09 '25 00:12

David Rodríguez - dribeas



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!