声明`using namespace C;`对于证明[namespace.udir]/3中的示例中显示的结果至关重要

Bel*_*loc 8 c++ language-lawyer

据我所知,using namespace C;命名空间中的以下声明对于编译器抱怨qual -id s 和下面的代码之间的歧义D必不可少的,这是[namespace.udir]/3中 C++标准中的一个例子:B::C::iA::i

namespace A {
  int i;
  namespace B {
    namespace C {
      int i;
    }
    using namespace A::B::C;
    void f1() {
      i = 5;        // OK, C?::?i visible in B and hides A?::?i
    }
  }
  namespace D {
    using namespace B;
    //using namespace C;
    void f2() {
      i = 5;        // ambiguous, B?::?C?::?i or A?::?i?
    }
  }
  void f3() {
    i = 5;          // uses A?::?i
  }
}
void f4() {
  i = 5;            // ill-formed; neither i is visible
}
Run Code Online (Sandbox Code Playgroud)

令人惊讶的是,当声明被注释掉代码时,所有三个编译器VS2017,GCC和clang都显示相同的错误消息using namespace C;.我错过了什么?

main.cpp:17:13: error: reference to 'i' is ambiguous
       i = 5;      // ambiguous, B::C::i or A::i?
Run Code Online (Sandbox Code Playgroud)

Sto*_*ica 5

歧义是由于早期的使用指令:

namespace B {
// ...
  using namespace A::B::C;
// ...
}
namespace D {
  using namespace B;
Run Code Online (Sandbox Code Playgroud)

由于using指令对于非限定查找是传递的([namespace.udir]/4).