Officially, what is typename for?

Following is the quote from Josuttis book:

The keyword typename was introduced to specify that the identifier that follows is a type. Consider the following example:

template <class T>
Class MyClass
{
  typename T::SubType * ptr;
  ...
};

Here, typename is used to clarify that SubType is a type of class T. Thus, ptr is a pointer to the type T::SubType. Without typename, SubType would be considered a static member. Thus

T::SubType * ptr

would be a multiplication of value SubType of type T with ptr.


Stan Lippman's BLog post suggests :-

Stroustrup reused the existing class keyword to specify a type parameter rather than introduce a new keyword that might of course break existing programs. It wasn't that a new keyword wasn't considered -- just that it wasn't considered necessary given its potential disruption. And up until the ISO-C++ standard, this was the only way to declare a type parameter.

So basically Stroustrup reused class keyword without introducing a new keyword which is changed afterwards in the standard for the following reasons

As the example given

template <class T>
class Demonstration {
public:
void method() {
    T::A *aObj; // oops …
     // …
};

language grammar misinterprets T::A *aObj; as an arithmetic expression so a new keyword is introduced called typename

typename T::A* a6;

it instructs the compiler to treat the subsequent statement as a declaration.

Since the keyword was on the payroll, heck, why not fix the confusion caused by the original decision to reuse the class keyword.

Thats why we have both

You can have a look at this post, it will definitely help you, I just extracted from it as much as I could


Consider the code

template<class T> somefunction( T * arg )
{
    T::sometype x; // broken
    .
    .

Unfortunately, the compiler is not required to be psychic, and doesn't know whether T::sometype will end up referring to a type name or a static member of T. So, one uses typename to tell it:

template<class T> somefunction( T * arg )
{
    typename T::sometype x; // works!
    .
    .