C++ Study Note (3) – typename, class and template

Development February 27th, 2007

C++ is strong type-safe language, the C++ compiler needs to check type and verify syntax correctness. C++ reuse the “*” as pointer dereference, also multiple, the template reuse the “< >“, which might be used in the stream “<<, >>” or logic operation, ( less than, great than ). C++ compiler may not figure out the ambiguous syntax meaning in some cases, for example:

template< class T, typename U> foo;

foo< int, vector<int>> v;  

// The following examples are copied from text book B1.1

iterator_traits<FwdIterator1>::value_type* pi = &*i;    

template <typename T, typename T::value_type>  struct sqrt_impl;  

{  return  x.convert<3>(pi);  }

Ln 1 demostrates either class or typename can be used to declare the template parameter.

Ln 2 shows a pitfall for “> >”, if there is no space between two >, the compiler would regards it as “>>” stream operator instead.

Ln 4 is a typical case when to use typename. The compiler could not determine whether

iterator_traits::value_type

is a type or a value. If it is a type, * would be the pointer decorator, otherwise, * is the multiplex. We need to help the compiler to clarify the ambiguousness by adding typename decorator like this:

typename iterator_traits::value_type

Ln 5 is the example of misusing typename as the template parameter. Since typename T::value_type could also regard as the typename declaration. The best approach is to use class only.

Ln 6 is the example when to use template keyword to disambiguate template. x.convert could be a template member function or member variable; therefore, the succeeding < > could interpreted as template or less than, great than operators. The work-around is like this:

{  return  x.template convert<3>(pi);  }

Here are some rules of thumbs:

  • typename is required anywhere in templates on qualified dependent names that denote type.
  • typename is forbidden on the name of base class.
  • template is required before dependent names accessing member templates via . , ->, or :: qualification.