§3.4.6/1:
在using-directive或namespace-alias-definition中,在查找命名空间名称或 嵌套名称说明符中的名称期间,仅考虑命名空间名称。
基本上,我要问的是:“为什么这一段是必要的?”
§3.4.6/1:
在using-directive或namespace-alias-definition中,在查找命名空间名称或 嵌套名称说明符中的名称期间,仅考虑命名空间名称。
基本上,我要问的是:“为什么这一段是必要的?”
缺陷报告 373:在 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 中查找命名空间名称时,仅考虑命名空间名称。
与我们今天所拥有的一样,因为原始措辞没有涵盖嵌套名称说明符。
歧义在于嵌套名称说明符,如果我们查看C++11 标准草案,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 ::
以及由于它们很大而我不会复制的以下段落不会将嵌套名称说明符限制为命名空间。
据我所知,7.3.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缺陷报告中也讨论了这个问题