Reputation: 908
Consider the following code:
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};
}
};
Why does foo1 work but not foo2? Is not the struct initializer constructor visible for class A? Is there anyway to make this work in C++11?
(Note, removing the private makes foo2 working.)
Upvotes: 1
Views: 651
Reputation: 206526
Why does
foo1
work but notfoo2
? Is not the struct initializer constructor visible for classA
?
B b = {0};
Does not work because B
is not an Aggregate. And it is not an Aggregate because it has an non-static private data member. If you remove the private specifier, B
becomes an Aggregate and hence can be initialized in this manner.
C++03 Standard 8.5.1 Aggregates
Para 7:
If there are fewer initializers in the list than there are members in the aggregate, then each member not explicitly initialized shall be value-initialized (8.5). [Example:
struct S { int a; char* b; int c; }; S ss = { 1, "asdf" };
initializes
ss.a
with1
,ss.b
with"asdf"
, andss.c
with the value of an expression of the formint()
, that is,0
. ]
C++03 standard 8.5.1 §1:
An aggregate is an array or a class (clause 9) with no user-declared constructors (12.1), no private or protected non-static data members (clause 11), no base classes (clause 10), and no virtual functions (10.3).
Upvotes: 3