成员的struct与命名空间的潜在范围

时间:2018-04-16 08:21:33

标签: c++ scope namespaces declaration

参考此代码:

namespace Y {
  char f() { return y; } // error: y was not declared in this scope
  char y;
}

struct X {
  char  f() { return x; } // OK
  char  x;
};

根据basic.scope.namespace#1

  

命名空间定义的声明性区域就是它   命名空间体。在名称空间体中声明的实体据说是   命名空间的成员以及这些声明引入的名称   进入命名空间的声明区域被称为成员   命名空间的名称。它的潜在范围包括来自名称的声明之后的名称空间

问题

  1. 说错误是因为Y::y尚未在Y::f()中声明{<1}}这是错误的吗?

  2. 我无法理解为什么namespace成员在声明期间没有“重新加载”struct。什么原因可能导致不允许这种行为? 标准是否有类似内容?

2 个答案:

答案 0 :(得分:5)

  

说错误是因为Y::y尚未在Y::f()中宣布这一事实,这是否正确?

  

我无法理解为什么没有&#34;重新加入&#34;声明中的命名空间成员,而对于struct而言。什么原因可能导致不允许这种行为?标准是否有相似之处?

命名空间与类相反的最大障碍是它们永远不会被关闭&#34;。您始终可以通过在另一个翻译单元中重新打开成员并在其中声明更多内容来将成员添加到名称空间。但是,对于其所有成员,类声明必须完全出现在单个翻译单元中。以后没有任何补充。

  

[class.mem]/1

     

类定义中的 member-specification 声明了完整集   班级成员;没有成员可以添加到其他地方。

命名空间的问题是难以处理的。但是课程只需要更多,非常本地化的工作。

因此,对于语言设计者和编译器编写者来说,要求命名空间声明在使用之前就更容易了。

您还应注意,您只能在定义中的一组特定位置使用该类的其他成员。

  

[class.mem]/6

     

一个类被认为是一个完全定义的对象类型([basic.types])   (或完整类型)在类说明符的结束}处。内   class member-specification ,该类被认为是完整的   函数体,默认参数,noexcept-specifiers和默认值   成员初始值设定项(包括嵌套类中的此类内容)。   否则在自己的班级中被认为是不完整的   构件的规范

答案 1 :(得分:3)

你错误地认为对于结构来说,有重新排序&#34;。

考虑以下结构定义。

#include <iostream>

struct A
{
    char s[N];
    enum { N = 10 };
};

int main() 
{
    return 0;
}

编译器将发出错误,因为在数组声明中使用时尚未声明名称N。所以既不重新排序&#34;存在于类范围内。对于成员函数,首先在类范围中搜索成员函数中使用的名称。

此外,在命名空间中声明的名称可以隐藏在外部命名空间中声明的相同名称。结果&#34;重新排序&#34;打破变量范围。