c++ - 为什么内联声明不是不完整的类型?

标签 c++ incomplete-type

考虑下面的代码:

struct Foo {
    struct Bar;
    Foo()
    {
        Bar bar; // Why isn't Bar an incomplete type?!
    }
    struct Bar {}; // Full definition
};

// struct Bar {}; // fails to compile due to incomplete type

int main()
{
    Foo foo;
}

它在至少 2 个编译器(gcc5.2、clang3.5)下编译得很好。我的问题是:

  • 为什么 Bar 在构造函数 Foo::Foo 中不被视为不完整类型,因为我在构造函数上方将其前向声明,但在构造函数内部完全使用它?

每当我将 Foo::Bar 移出类,换句话说 Bar 成为一个独立的类时,我都会得到预期的

error: aggregate 'Foo::Bar bar' has incomplete type and cannot be defined

最佳答案

在成员规范中,类在函数体中被认为是完整的,来自草案 C++ 标准部分 9.2 [class.mem]:

A class is considered a completely-defined object type (3.9) (or complete type) at the closing } of the class-specifier. Within the class member-specification, the class is regarded as complete within function bodies, default arguments, using-declarations introducing inheriting constructors (12.9), exception-specifications, and brace-or-equal-initializers for non-static data members (including such things in nested classes). Otherwise it is regarded as incomplete within its own class member-specification

这意味着您甚至不必转发声明 Bar ( see it live ):

struct Foo {
    Foo()
    {
        Bar bar; 
    }
    struct Bar {};  
};

前向声明有助于避免违反 3.3.7 paragraph 2 and 3 部分.

关于c++ - 为什么内联声明不是不完整的类型?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32685319/

相关文章:

c++ - if 条件下两个字符串比较的优化代码

c - 不完整数组类型的 p[0] 和 *p 等价

c++ - 不完整类型的无效使用/错误的前向声明。可能误用抽象类? (C++)

java - 字符串无法转换为数组

C++ - 循环依赖(在模板化基类中使用子类的内部类型)

c++ - 如何在不使用 std::string 或任何 STL 的情况下将复数存储在 C++ 的字符数组中?

c++ - 为什么这个简单的 C++ 代码不能编译?

c++ - Meyers 提出的 MCU 寄存器抽象的新布局

c++ - 错误 : cannot convert 'int (*)[(((sizetype)(((ssizetype)n) + -1)) + 1)]' to 'int (*)[100]' for argument '1' to 'int determ(int (*)[100], int)' |

C:允许将任何数组分配给指向不完整类型数组的指针