3758. Element-relocating operations of std::vector and std::deque should conditionally require Cpp17CopyInsertable in their preconditions

Section: 23.3.11.3 [vector.capacity], 23.3.11.5 [vector.modifiers], 23.3.5.3 [deque.capacity], 23.3.5.4 [deque.modifiers] Status: New Submitter: Jiang An Opened: 2022-08-24 Last modified: 2022-11-06

Priority: 3

View other active issues in [vector.capacity].

View all other issues in [vector.capacity].

View all issues with New status.

Discussion:

This issue is raised from editorial issue #5776.

In order to achieve strong exception safety, some operations of std:vector and std::deque may use copy insertion for relocation of old elements, if move construction of its element type is potentially throwing and copy insertion is available. However, currently only Cpp17MoveInsertable is mentioned in many of their Preconditions (e.g. those of insert for rvalues), which seemly fails to cover the cases in which copy insertion is formally invalid but the semantic requirements of Cpp17CopyInsertable are not met.

Perhaps we should create a new named requirement for these operations, which is equivalent to Cpp17CopyInsertable when !is_nothrow_move_constructible_v<T> && is_copy_constructible_v<T> is true, and equivalent to Cpp17MoveInsertable otherwise.

[2022-09-23; Reflector poll]

Set priority to 3 after reflector poll.

Jonathan: I think the point (which LWG 3758 fails to explain clearly) is that today's implementations sometimes use copy insertion when move insertion is syntactically valid, but is potentially-throwing. But the preconditions don't require copy insertion. If vector::resize(size_type) decides to use copy construction, because move construction might throw and the type is copy constructible (which is implied to be permitted by the Remarks), do we require Cpp17CopyInsertable's semantic requirement that the new value is equivalent to the one we copied? We don't say so.
tl;dr The user is trying to resize a vector and the value type is Cpp17MoveInsertable into the vector, but the implementation decides to copy not move. What are the preconditions on the user's type?

[2022-11-06; Daniel comments]

This issue has considerable overlap with LWG 2158.

Proposed resolution: