1

I looked up on Wiki for the keyword typename (http://en.wikipedia.org/wiki/Typename) and it gives an example which typename is required before T::bar

template <typename T>
void foo(const T& t)
{
   // declares a pointer to an object of type T::bar
   T::bar * p;
}

struct StructWithBarAsType {
   typedef int bar;
};

int main() {
   StructWithBarAsType x;
   foo(x);
}

Why doesn't C++ inspect StructWithBarAsType and find that T::bar is actually a type when generating code for foo(x)? Is it not possible or just an efficiency consideration?

delphifirst
  • 1,535
  • 12
  • 20

2 Answers2

1

it assumes that T::bar is a static member unless typename is specified beforehand. afaict there is no technical limitation that would prevent compilers from being able to figure out during instantiation whether or not T::bar is a type, but to keep things a bit easier for compiler implementors, the decision was made. It can make more of a difference than than one might think, consider

T::bar<a,b>c;

is this a variable c of type T::bar<a,b>, or is it a less than, comma, greater than? T::bar < a followed by b > c? C++ template syntax leaves a lot to be desired.

Ryan Haining
  • 30,835
  • 10
  • 95
  • 145
1

When parsing a template it may genuinely be impossible to determine whether a type or value is intended. An example is

int v = 2;
template <typename T>
void f() {
    T::value * v;
}

This code may either declare a pointer or imply an operation. Neither interpretation is particular useful. When the compiler is asked to make sense of this code it doesn't know the type T. Now, you could say: have it be prepared for both interpretation! ... but you would have a combinatorial explosion at hand if the next lines carry on with something similar.

I could imagine the compilers could in most cases correctly determine what is meant. However, without further context it is sometimes impossible. At the time typename was introduced I also think it was unexpected how often it is needed. To some extend that got fixed by auto and decltype(...) which get rid of many needs for nested types.

TheCodeArtist
  • 19,131
  • 3
  • 60
  • 123
Dietmar Kühl
  • 141,209
  • 12
  • 196
  • 356