Gre*_*ree 12 c++ standards templates name-lookup
来自temp.local:
在出现在类模板定义之外的类模板成员的定义中,类模板成员的名称隐藏任何封闭类模板的模板参数的名称(但不是模板参数的名称)成员,如果成员是类或函数模板).[例如:
Run Code Online (Sandbox Code Playgroud)template<class T> struct A { struct B { /* ... */ }; typedef void C; void f(); template<class U> void g(U); }; template<class B> void A<B>::f() { B b; // A's B, not the template parameter } template<class B> template<class C> void A<B>::g(C) { B b; // A's B, not the template parameter C c; // the template parameter C, not A's C }- 结束例子]
问题是,我尝试过的每个编译器(g ++,vc,icc,clang)都将C A<B>::g(C)作为A的成员名称处理,并且不编译该示例.
这是一个常见的错误吗?
虽然您提供的链接似乎是草案并明确声明它不属于任何标准 ( http://eel.is/c++draft/ ),但草案中的这一特定条款似乎与 ISO C++ 相同14.6.1,第 7 段。
因此,它确实看起来要么是一个常见的编译器错误,要么是一个与其他子句冲突并丢失的子句。我验证了该示例无法在 MacOS Clang v802.0.42 上编译。既然你说所有主要编译器都在这里发出错误,我怀疑由于与其他一些子句冲突,该子句的实现不合理。
编辑:我还在标准社区中发现了与此主题相关的讨论。在我看来,这里讨论的深度表明这条规则是有争议的,甚至可能会改变。