According to 12.1 [class.ctor] paragraph 4 says,
A defaulted default constructor for class X is defined as deleted if:
X is a union-like class that has a variant member with a non-trivial default constructor,
...
This should make the following example ill-formed:
struct S {
S();
};
union U {
S s{};
} u;
because the default constructor of U is deleted. However, both clang and g++ accept this without error. Should the rule be relaxed for a union with an NSDMI?
Notes from the May, 2015 meeting:
An NSDMI is basically syntactic sugar for a mem-initializer, so the presence of one should be treated as if a user-declared default constructor were present.
Proposed resolution (October, 2015):
Change 12.1 [class.ctor] paragraph 4 as follows:
...A defaulted default constructor for class X is defined as deleted if:
X is a union that has a variant member with a non-trivial default constructor and no variant member of X has a default member initializer,
X is a union-like non-union class that has a variant member M with a non-trivial default constructor and no variant member of the anonymous union containing M has a default member initializer,
...
DR 2084:2084. NSDMIs and deleted union default constructors
Section: 12.1 [class.ctor] Status: ready Submitter: Daveed Vandevoorde Date: 2015-02-12According to 12.1 [class.ctor] paragraph 4 says,
A defaulted default constructor for class X is defined as deleted if:
X is a union-like class that has a variant member with a non-trivial default constructor,
...
This should make the following example ill-formed:
struct S { S(); }; union U { S s{}; } u;
because the default constructor of U is deleted. However, both clang and g++ accept this without error. Should the rule be relaxed for a union with an NSDMI?
Notes from the May, 2015 meeting:
An NSDMI is basically syntactic sugar for a mem-initializer, so the presence of one should be treated as if a user-declared default constructor were present.
Proposed resolution (October, 2015):
Change 12.1 [class.ctor] paragraph 4 as follows:
...A defaulted default constructor for class X is defined as deleted if:
X is a union that has a variant member with a non-trivial default constructor and no variant member of X has a default member initializer,
X is a union-like non-union class that has a variant member M with a non-trivial default constructor and no variant member of the anonymous union containing M has a default member initializer,
...
I don't understand the reason for the change in the first bullet point above, as the snippet will continue to be ill-formed: U is a union with a variant member (s) with a non-trivial default constructor (the default constructor for S is user-provided) and no variant member of U has a default member initializer (S doesn't have a default member initializer, according to the definition of this term in [class.mem]/8.
There is no member of S that has a default member initializer, but `U::s` does. And that's what the bullet point is looking for: a member of the union that has a DMI.
we conclude that the defaulted default constructor for U must be defined as deleted.
--
---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Discussion" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-discussion+unsubscribe@isocpp.org.
To post to this group, send email to std-dis...@isocpp.org.
Visit this group at https://groups.google.com/a/isocpp.org/group/std-discussion/.
On Tuesday, November 15, 2016 at 12:57:06 PM UTC-2, Nicol Bolas wrote:
There is no member of S that has a default member initializer, but `U::s` does. And that's what the bullet point is looking for: a member of the union that has a DMI.First off, the Standard does not define the term DMI.
Second, the bullet point does not mention DMI nor NSDMI, but it mentions "default member initializer" which is defined in [class.mem]/8. And last, but not the least, this is not what the bullet point is saying, as far as I can understand:U is a union that has a variant member (s) with a non-trivial default constructor (this is correct, as the default constructor for S is not user-provided) and no variant member of U (U has just one variant member - s) has a default member initializer.As s is the sole variant member of U and since S has no default member initializer, we conclude that the defaulted default constructor for U must be defined as deleted.
Are you really going to quibble about an obvious acronym of the term "default member initializer"?
Types cannot have DMIs; members of types have default member initializer. `U::s` is a "variant member of U". And `U::s` has a DMI.
On Tuesday, November 15, 2016 at 1:23:23 PM UTC-5, Belloc wrote:On Tuesday, November 15, 2016 at 12:57:06 PM UTC-2, Nicol Bolas wrote:
There is no member of S that has a default member initializer, but `U::s` does. And that's what the bullet point is looking for: a member of the union that has a DMI.First off, the Standard does not define the term DMI.
Are you really going to quibble about an obvious acronym of the term "default member initializer"?
Second, the bullet point does not mention DMI nor NSDMI, but it mentions "default member initializer" which is defined in [class.mem]/8. And last, but not the least, this is not what the bullet point is saying, as far as I can understand:U is a union that has a variant member (s) with a non-trivial default constructor (this is correct, as the default constructor for S is not user-provided) and no variant member of U (U has just one variant member - s) has a default member initializer.As s is the sole variant member of U and since S has no default member initializer, we conclude that the defaulted default constructor for U must be defined as deleted.
Types cannot have DMIs; members of types have default member initializer. `U::s` is a "variant member of U". And `U::s` has a DMI.
--
struct S {
S();
};
union U {
S s;
int i = 1;
} u;
A defaulted default constructor for class X is defined as deleted if:
No, the Note is more strict than the bullet point. The note specifies more types that will have deleted default constructors than the actual specification. The Note is more restrictive than the normative text.
So the notation should be changed or removed.
https://github.com/cplusplus/draft/issues/1073 filed to fix the note.