§3.4.6/ 1:
在 using-directive 或 namespace-alias-definition 中, 查找名称空间名称或查找名称 nested-name-specifier 仅考虑名称空间名称。
基本上,我要问的是:“为什么这个段落是必要的?”
答案 0 :(得分:2)
Defect report 373: Lookup on namespace qualified name in using-directive举例说明了措辞的重要性:
namespace X {
namespace Y {
struct X {
void f()
{
using namespace X::Y;
namespace Z = X::Y;
}
};
}
}
在X
结构或命名空间中引用了哪个using namespace X::Y
?如果3.4.6
中没有这样的措辞,那将是模棱两可的。
这实际上导致了措辞的改变:
在using-directive或namespace-alias-definition中查找namespace-name时,只考虑名称空间名称。
我们今天所拥有的,因为原始措辞没有涵盖嵌套名称说明符。
歧义是使用嵌套名称说明符,如果我们查看5.1.1
部分nested-name-specifier:
::opt type-name ::
::opt namespace-name ::
decltype-specifier ::
nested-name-specifier identifier ::
nested-name-specifier templateopt simple-template-id ::
一般中的draft C++11 standard语法,则为如下:
7.3.1
以及我不会复制的以下段落,因为它们很大,不会将嵌套名称说明符限制为名称空间。
据我所知,{{1}} 命名空间定义足以限制 namespace-name 以防止出现歧义。
答案 1 :(得分:1)
Clang对namespace using
和alias directives
的单元测试正是您问题的答案:
clang-cc -fsyntax-only -verify%s
struct ns1 {}; // This is not a namespace, although a namespace has ns1 as a name
void ns2();
int ns3 = 0;
namespace ns0 {
namespace ns1 {
struct test0 {};
}
namespace ns2 {
struct test1 {};
}
namespace ns3 {
struct test2 {};
}
}
using namespace ns0;
namespace test3 = ns1; // don't get confused
namespace test4 = ns2;
namespace test5 = ns3;
using namespace ns1; // don't get confused
using namespace ns2;
using namespace ns3;
test0 a;
test1 b;
test2 c;
此问题也在n3160 defect report
中讨论过