【问题标题】:Why does the name lookup does not stop when it finds the entity implicitly declared by using directive?为什么名称查找在找到使用指令隐式声明的实体时不会停止?
【发布时间】:2018-03-16 05:11:24
【问题描述】:

下面是代码示例:

#include<iostream>
using namespace std;
namespace B
{
  int ohoh=2;
}

namespace A
{
  int ohoh=666;
  namespace C 
  {
      //using B::ohoh;(as if declared by using directive) //why does the lookup not stops here?
      int foo()
      {
        using namespace B;
        cout<<ohoh<<endl;
      }
  }
}

int main()
{
    A::C::foo();
}  

输出是 666 但不是 2。为什么?

引自cppref

对于非限定名称,即没有出现在范围解析运算符 :: 右侧的名称,名称查找会按如下所述检查范围,直到找到至少一个任何类型的声明,此时查找停止并且不再检查范围。(注意:从某些上下文中查找会跳过某些声明,例如,查找 :: 左侧使用的名称会忽略函数、变量和枚举器声明, 查找用作基类说明符的名称会忽略所有非类型声明)

出于非限定名称查找的目的,由 using 指令指定的命名空间中的所有声明似乎都在最近的封闭命名空间中声明,该命名空间直接或间接包含 using 指令和指定的命名空间。

从上面引用的段落中,名称查找应该停止在最近的namespace C,我在代码中注释的地方。为什么它没有停止并找到A::ohoh

顺便说一句,我觉得应该尽量少用using指令。

【问题讨论】:

    标签: c++ using-directives name-lookup


    【解决方案1】:

    出于非限定名称查找的目的,来自 using 指令指定的命名空间的所有声明如同在最近的封闭命名空间中声明,其中包含 [...] using 指令和指定的命名空间强>。

    在这种情况下,包含B 和 using 指令的最近命名空间是全局命名空间。因此,来自B 的所有名称都出现在A::C::foo 中,就好像它们是在全局命名空间中声明的一样。搜索名称 ohoh 时,A 会在全局命名空间之前搜索,因此 A::ohoh 是找到的第一个声明,名称查找将在此处停止。

    【讨论】:

    • 他的注释语句实际上是一个 using 声明
    • 原来如此,我以前认为最近的命名空间是C
    • @PasserBy 从这个问题来看,我觉得这只是为了展示。那就是OP认为应该注入名称的地方。不过,我可能误解了这个问题。
    • @PasserBy 我只是把该评论显示为我理解的最近的命名空间。
    • @PasserBy 从我引用的内容来看,我认为“as if declared”与using declaration 具有相同的效果,这也是一种声明。跨度>
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-04-24
    • 1970-01-01
    • 1970-01-01
    • 2021-11-20
    • 2011-03-21
    相关资源
    最近更新 更多