emplace
broken for associative containersSection: 23.2.8 [unord.req] Status: NAD Submitter: Pablo Halpern Opened: 2010-10-18 Last modified: 2016-01-28
Priority: Not Prioritized
View other active issues in [unord.req].
View all other issues in [unord.req].
View all issues with NAD status.
Discussion:
The current definition of emplace(args)
for associative containers as
described in Table 99 is:
Requires:
Effects: Inserts aT
shall be constructible fromargs
.T
objectt
constructed withstd::forward<Args>(args)...
if and only if there is no element in the container with key equivalent to the key oft
. Thebool
component of the returnedpair
istrue
if and only if the insertion takes place, and the iterator component of thepair
points to the element with key equivalent to the key oft
.
There is similar language in Table 100 for unordered associative containers.
The first issue is editorial:T
should be value_type
throughout
both tables.
The major issue is that, if the container is map
, multimap
,
unordered_map
, or unordered_multimap
, then the only way to
construct an object of value_type
is to supply exactly two arguments
for Key
and Value
, a pair<Key,Value>
, or a
piecewise_construct_t
followed by two tuple
s. The original
emplace()
proposal would have allowed you to specify a Key
value followed by any number of constructor arguments for Value
.
When we removed the variadic constructor to pair
, this ability went
away. I don't think that was deliberate.
Fixing this is non-trivial, I think. I think that emplace()
for map
and multimap
need several overloads: one for each overloaded constructor in
pair<Key,Value>
, and one for the emplace(Key, valueargs...)
case.
And it probably needs some SFINAE meta-programming to ensure that the last case
doesn't override any of the other ones. Alternatively, one could say that
there are exactly two cases: emplace(args)
where pair<Key,Value>
is constructible from args
, and emplace(args)
where Key
is
constructible form the first arg
and Value
is constructible from the
rest.
Alternatively, the status quo is to use piecewise_construct_t
if you want to
construct an object.
[ 2010 Batavia: ]
N3178 was looked at in session and moved to NAD.
Proposed resolution: