1

考虑以下代码:

class A
{
private:
    struct B { private: int i; friend class A; };

public:
    static void foo1()
    {
        B b;
        b.i = 0;
    }

    static void foo2()
    {
        B b = {0};
    }
};

为什么foo1有效但foo2无效?struct initializer 构造函数对 A 类不可见吗?无论如何可以在 C++11 中完成这项工作吗?

(注意,删除 private 会使 foo2 工作。)

4

1 回答 1

3

为什么foo1有效但无效foo2?struct initializer 构造函数对 class 不可见A吗?

B b = {0};

不起作用,因为B不是Aggregate。而且它不是聚合,因为它具有非静态私有数据成员。如果您删除私有说明符,B则成为聚合,因此可以以这种方式初始化。


C++03 标准 8.5.1 聚合
第 7 段:

如果列表中的初始化器少于聚合中的成员,则每个未显式初始化的成员都应进行值初始化(8.5)。[例子:

 struct S { int a; char* b; int c; };
 S ss = { 1, "asdf" };

ss.a使用、 和形式的表达式的值进行初始化1,即. ]ss.b"asdf"ss.cint()0

C++03 标准 8.5.1 §1

聚合是一个数组或一个类(第 9 条),没有用户声明的构造函数(12.1),没有私有或受保护的非静态数据成员(第 11 条),没有基类(第 10 条),也没有虚函数(10.3) )。

于 2012-11-25T13:54:59.250 回答