Subclass Pattern Types in Pattern

I have a class that comes from a template class:

template <typename A,typename B>
class TemplatedClass {

};

class Hello : public TemplatedClass<int,float>
{

};

Now I want to create a template class that will infer int, float types from Hello.
I thought I could do something like this, but this will not work:

template <template <typename A,typename B> class C>
class Check
{
    void Foo(A,B,C)
    {
        // A is int .. B is float .. C is Hello
    }
};



int _tmain(int argc, _TCHAR* argv[])
{
    Check<Hello> a;
}

How can i do this?

Edit:

I want to pass the Hello class and get a template that infers the types used by its TemplatedClass subclass .

So when I create the class Check<Hello>, it will get the int and float types

I cannot change TemplatedClass to include typedefs (this is from an external .lib)

Edit:

, , :
C3200: "Hello": "C",

+3
5

typename class, ยง14.1 [temp.param] p1:

-:

  • opt
  • opt= type-id
  • typename opt
  • typename opt= type-id
  • template < template-parameter-list > class opt
  • template < template-parameter-list > class opt= id-expression

:

template<class T>
class Check;

template< // not 'typename'   vvvvv
  template<typename,typename> class C,
  typename A, typename B
>
struct Check<C<A,B> >{
  // ...
};

Hello , Hello TemplatedClass, :

Check<Hello> c; // nope, 'Hello' is not a template

typedef Hello:

class Hello
  : TemplatedClass<int,float>
{
public:
  typedef TemplatedClass<int,float> base_type;
};

:

c;// C Check template TemplatedClass, Hello. , . , :

template<class T>
class CheckInternal;

template<
  template<typename,typename> class C,
  typename A, typename B
>
class CheckInternal<C<A,B> >{
  public:
     typedef A type_A;
     typedef B type_B;
};

template<class T>
class Check{
  typedef typename T::base_type T_base_type;
  typedef typename CheckInternal<T_base_type>::type_A type_A;
  typedef typename CheckInternal<T_base_type>::type_B type_B;

  void foo(type_A a, type_B b){
    // ...
  }
};

// usage:
C<Hello> c; // OK!
+3

- :

template <template <typename A,typename B> typename C>
class Check
{
     template<typename A, typename B>
     void Foo(A a, B b) {
        // C<A,B> would reconstruct the template type
     }
}

// use: 
Check<Hello> a;
a.Foo(true,1.f);

, , ( , ):

template <typename A,typename B>
class TemplatedClass {
   typedef A TypeA;
   typedef B TypeB;
};


template <typename C>
class Check
{

     void Foo(typename C::TypeA& a, typename C::TypeB&) {}
}

// use: 
Check<Hello<int,float> > a;
a.Foo(1,1.f);
+3

- :

template <typename A,typename B>
class TemplatedClass {
public:    
    typedef A firstType;
    typedef B secondType;
};

class Hello : public TemplatedClass<int,float>
{
public:    
    typedef firstType Type1;
    typedef secondType Type2;
};

template <typename C>
class Check
{
    typedef typename C::Type1 A;
    typedef typename C::Type2 B;

    void Foo(A,B,C)
    {
        // A is int .. B is float .. C is Hello
    }
};
+1

, , Hello, . - :

template <typename A, typename B>
class HelloBase : public TemplatedClass<A, B>
{
public:    
    typedef A Type1;
    typedef B Type2;
};

typedef HelloBase<int, float> Hello;

template <typename C>
class Check
{
    typedef typename C::Type1 A;
    typedef typename C::Type2 B;

    void Foo(A,B,C)
    {
        // A is int .. B is float .. C is Hello
    }
};

...

Check<Hello> a;

So the TemplatedClass does not need to be changed, and you can put everything that you are going to put in Hello in HelloBase (using the template for the tool for simple type transfer).

+1
source

What you want is impossible in the general case - what if Helloreceived from TemplatedClasstwice?

This, however, is pretty simple to do, not even intrusive, in C ++ 0x.

template<typename A, typename B> struct retval {
    typedef A first;
    typedef B second;
};
template<typename one, typename two> one first(const TemplatedClass<one, two>& ref);
template<typename one, typename two> two second(const TemplatedClass<one, two>& ref);
template<typename T> class Check {
    typedef decltype(first(*static_cast<T*>(nullptr))) first;
    typedef decltype(second(*static_cast<T*>(nullptr))) second;
};

In C ++ 03, you can still get the parameters inside the method, but you cannot access them outside unless you insert special typedefs.

+1
source

All Articles