以下代码:
struct foo {};
struct A
{
typedef foo foo_type;
void foo();
};
GCC给出了编译错误:
test.cpp:7:14: error: declaration of 'void A::foo()' [-fpermissive]
void foo();
^
test.cpp:1:8: error: changes meaning of 'foo' from 'struct foo' [-fpermissive]
struct foo {};
^
但clang接受它没有编译器错误。谁是对的?
请注意,如果删除了typedef,或将其更改为typedef ::foo foo_type
,则gcc和clang都接受代码。
答案 0 :(得分:18)
gcc是正确的,但是clang不需要提供诊断(3.3.7):
类S中使用的名称N应引用其中的相同声明 上下文,并在完成范围内重新评估 违反此规则需要诊断。
这是因为类范围的工作原理。 foo
void foo();
A
在类void foo();
的整个范围内可见,因此foo
的声明更改了{{1}的含义在typedef中引用struct foo
到函数foo
的名称。