Title
std::function move constructor does unnecessary work
Status
c++17
Section
[func.wrap.func.con]
Submitter
Geoffrey Romer

Created on 2016-12-15.00:00:00 last changed 89 months ago

Messages

Date: 2017-01-30.15:36:02

Proposed resolution:

This wording is relative to N4618.

  1. Edit [func.wrap.func.con]/5 as indicated:

    Drafting note: The "equivalent to ... before the construction" wording is based on the wording for MoveConstructible.

    function(function&& f);
    

    -5- EffectsPostconditions: If !f, *this has no target; otherwise, move constructs the target of f into the target of *this, leaving fthe target of *this is equivalent to the target of f before the construction, and f is in a valid state with an unspecified value.

Date: 2017-01-27.00:00:00

[ 2017-01-27 Telecon ]

Priority 0

Date: 2016-12-15.00:00:00

Consider [func.wrap.func.con]/p5:

function(function&& f);

Effects: If !f, *this has no target; otherwise, move constructs the target of f into the target of *this, leaving f in a valid state with an unspecified value.

By my reading, this wording requires the move constructor of std::function to construct an entirely new target object. This is silly: in cases where the target is held in separately allocated memory (i.e. where the target doesn't fit in std::function's internal buffer, if any), std::function's move constructor can be implemented by simply transferring ownership of the existing target object (which is a simple pointer assignment), so this requirement forces an unnecessary constructor invocation and probably an unnecessary allocation (the latter can be avoided with something like double-buffering, but ew). Fixing this would technically be a visible change, but I have a hard time imagining reasonable code that would be broken by it, especially since both libstdc++ and libc++ already do the sensible thing, constructing a new target only if the target is held in an internal buffer, and otherwise assigning pointers.

History
Date User Action Args
2017-07-30 20:15:43adminsetstatus: wp -> c++17
2017-03-05 23:41:16adminsetstatus: ready -> wp
2017-01-30 15:36:02adminsetmessages: + msg8826
2017-01-30 15:36:02adminsetstatus: new -> ready
2017-01-23 20:07:02adminsetmessages: + msg8781
2016-12-15 00:00:00admincreate