Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Template argument name resolution and compiler discrepancies

101 views
Skip to first unread message

Jonathan Jones

unread,
Sep 12, 2015, 12:30:07 PM9/12/15
to

Hi folks,

Look at the following example code:

template<typename>
class Base
{
typedef int ValueType;
};

template<typename ValueType>
struct Derived : public Base<ValueType>
{
Derived(ValueType);
};

Derived<float> obj(1);

This code compiles cleanly with GCC 4.7.2 and Clang 3.5 (Xcode 6.2).
However, it fails to compile with Visual Studio 2013, complaining that it
cannot access private typedef "Base<ValueType>::ValueType".

Furthermore, if you make the private typedef public:

template<typename>
class Base
{
public:
typedef int ValueType;
};

It compiles on all three compilers, but the produces different answers.
GCC and clang result in ValueType=float in the Derived constructor
definition, whereas Visual Studio 2013 results in ValueType=int in the
Derived constructor definition.

What does the standard say should happen in these cases? Which compiler(s)
are closer to implementing the standard behavior?

The standard is clear (see C++11 section 14.6.1 paragraph 9) about what
happens when "Base" is not a template, but it seems more vague about when
"Base" is a template (which the example above seems to demonstrate).

Sincerely,
Jonathan Jones


--
[ comp.std.c++ is moderated. To submit articles, try posting with your ]
[ newsreader. If that fails, use mailto:std-cpp...@vandevoorde.com ]
[ --- Please see the FAQ before posting. --- ]
[ FAQ: http://www.comeaucomputing.com/csc/faq.html ]

Bo Persson

unread,
Sep 13, 2015, 9:00:11 AM9/13/15
to
I would use different names when Base::ValueType is not the same as
Derived::ValueType. :-)


Otherwise, I suspect this is one symptom of VC++ failing to do a proper
2-phase name lookup. When Base is a template, its ValueType should not be
visible in the declaration of Derived(ValueType). If VC++ postpones the
name lookup until the template is instantiated, it WILL be visible at that
point.

However, as you say, when Base is not a template its ValueType will shadow
the template parameter in Derived. That's one reason for using a different
name.


Bo Persson
0 new messages