Using the model name without parameters

advertisements

I have this code:

template <typename A>
class templatedclass {
    public:
    using type = templatedclass;
};

template <typename A>
class sinkstuff {
    public:
    void print() {
        cout << "generic sinkstuff";
    }
};
template <typename A>
class sinkstuff <templatedclass<A>> {
    public:
    void print() {
        cout << "partiallyspecialized sinkstuff";
    }
};

template <typename NtoA>
struct pass_parameter : sinkstuff<typename templatedclass<NtoA>::type> {}; 

int main() {
  pass_parameter<int> obj;
  obj.print();
  cout << is_same<templatedclass<int>, typename templatedclass<int>::type>::value; // 1, yes
}

I always thought the "using directive" was a typedef on steroids. How come I can use "templatedclass<int>::type" without specifying the parameter again, i.e. "templatedclass<int>::type<int>" ?

Isn't "using type = templatedclass" just a textual substitution? Am I missing something?


The name of a class is "injected" into the class, this is called the injected-class-name. It is similar to:

class my_class_name
{
public:
    typedef ::my_class_name my_class_name;
};

(But this of course doesn't compile, a class may not have a manually declared member of the same name as the class.)

Class templates also have an injected-class-name, and it can be used to refer to the class template itself, or the current specialization (including the current template arguments), depending on the context:

[temp.local]/1

Like normal (non-template) classes, class templates have an injected-class-name. The injected-class-name can be used as a template-name or a type-name. When it is used with a template-argument-list, as a template-argument for a template template-parameter, or as the final identifier in the elaborated-type-specifier of a friend class template declaration, it refers to the class template itself. Otherwise, it is equivalent to the template-name followed by the template-parameters of the class template enclosed in <>.