nullopt_t insufficiently constrainedSection: 22.5.5 [optional.nullopt] Status: C++17 Submitter: Tim Song Opened: 2016-06-17 Last modified: 2017-07-30
Priority: 2
View all other issues in [optional.nullopt].
View all issues with C++17 status.
Discussion:
22.5.5 [optional.nullopt]/2 requires of nullopt_t that
Type
nullopt_tshall not have a default constructor. It shall be a literal type. Constantnulloptshall be initialized with an argument of literal type.
This does not appear sufficient to foreclose the following implementation:
struct nullopt_t
{
constexpr nullopt_t(const nullopt_t&) = default;
};
constexpr nullopt_t nullopt(nullopt_t{});
nullopt_t has no default constructor because it has a user-declared (copy) constructor;nullopt_t has a trivial destructor, is an aggregate, and is a literal type;nullopt has been initialized with an argument of literal type, to wit, nullopt_t.
But such a nullopt_t is still constructible from {} and so still makes opt = {} ambiguous.
[2016-08 Chicago]
This is related to LWG 2510.
Monday PM: Ville to provide updated wording
Fri AM: Moved to Tentatively Ready
Proposed resolution:
This wording is relative to N4606.
Edit 22.5.5 [optional.nullopt]/2 as indicated:
[Drafting note:
{}can do one of three things for a class type: it may be aggregate initialization, it may call a default constructor, or it may call an initializer-list constructor (see 9.5.5 [dcl.init.list], 12.2.2.8 [over.match.list]). The wording below forecloses all three possibilities. — end drafting note]
-2- Type
nullopt_tshall not have a default constructor or an initializer-list constructor. It shall not be an aggregate and shall be a literal type. Constantnulloptshall be initialized with an argument of literal type.