Is the following code legal? MSVC 9 and g++ 4.4 disagree:
struct base
{
struct derived {};
};
struct derived : base {};
int main()
{
typedef derived::derived type;
return 0;
}
MSVC complains, confusing the nested name for the type’s constructor:
c:\dev>cl test.cpp
Microsoft (R) 32-bit C/C++ Optimizing Compiler Version 15.00.30729.01 for 80x86
Copyright (C) Microsoft Corporation. All rights reserved.
test.cpp
test.cpp(10) : error C2146: syntax error : missing ';' before identifier 'type'
test.cpp(10) : error C2761: '{ctor}' : member function redeclaration not allowed
test.cpp(10) : error C2065: 'type' : undeclared identifier
While g++ does not:
$ g++ --version test.cpp
g++ (Ubuntu/Linaro 4.4.4-14ubuntu5) 4.4.5
Copyright (C) 2010 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
For context, my code contains an iterator called pointer. To provide the iterator interface, it provides the nested type pointer, which is a synonym for itself.
Comeau thinks that your code is incorrect, so I think that the constructor-interpretation shadowing the type-interpretation is what the standard mandates1.
Still, your code happily compiles if you clear up the ambiguity and tell the compiler that you’re trying to access the
derivedmember of the base class:By the way, the fact that the constructor-interpretation prevails kinda makes sense: you have a well-known way to tell the compiler that you want to refer to stuff of the base class (via the scope resolution operator), but you wouldn’t have a syntax to do the reverse (forcing the compiler to understand that you’re referring to the constructor). So the “constructor-by-default” behavior seems quite sensible.