Questions tagged [copy-elision]

Copy elision refers to an exception to the as-if rule allowing to omit copies

Copy Elision is an exception to the as-if rule governing the behavior of C++ programs.

Return-value-optimization is copy-ellision applied to value-returns.

12.8 Copying and moving class objects [class.copy]

31 When certain criteria are met, an implementation is allowed to omit the copy/move construction of a class object, even if the constructor selected for the copy/move operation and/or the destructor for the object have side effects. In such cases, the implementation treats the source and target of the omitted copy/move operation as simply two different ways of referring to the same object, and the destruction of that object occurs at the later of the times when the two objects would have been destroyed without the optimization.123
This elision of copy/move operations, called copy elision, is permitted in the following circumstances (which may be combined to eliminate multiple copies):

  • in a return statement in a function with a class return type, when the expression is the name of a non-volatile automatic object (other than a function or catch-clause parameter) with the same cv-unqualified type as the function return type, the copy/move operation can be omitted by constructing the automatic object directly into the function’s return value
  • in a throw-expression, when the operand is the name of a non-volatile automatic object (other than a function or catch-clause parameter) whose scope does not extend beyond the end of the innermost enclosing try-block (if there is one), the copy/move operation from the operand to the exception object (15.1) can be omitted by constructing the automatic object directly into the exception object
  • when a temporary class object that has not been bound to a reference (12.2) would be copied/moved to a class object with the same cv-unqualified type, the copy/move operation can be omitted by constructing the temporary object directly into the target of the omitted copy/move
  • when the exception-declaration of an exception handler (Clause 15) declares an object of the same type (except for cv-qualification) as the exception object (15.1), the copy operation can be omitted by treating the exception-declaration as an alias for the exception object if the meaning of the program will be unchanged except for the execution of constructors and destructors for the object declared by the exception-declaration.
272 questions
5
votes
3 answers

In c++11, can a virtual function return a large value efficiently with move semantics?

Normally, this would be optimised to not involve copying the large value (since a std::vector has move semantics enabled): std::vector makeABigThing(){ std::vector large_thing(1000, 0); return large_thing; } Can this also be…
James
  • 24,676
  • 13
  • 84
  • 130
4
votes
2 answers

Copy constructor elision?

Possible Duplicate: Why has the destructor been called only once? Given the code below, I fail to understand the output in gcc. I expect two objects to be created and destroyed but instead see only one call to the constructor and the destructor.…
Chubsdad
  • 24,777
  • 4
  • 73
  • 129
4
votes
0 answers

Object pointer (this) saved in the constructor for later use seems to have incorrect value

I came across a strange bug today, which basically boils down to the following minimal example: #include struct S* ps; struct S{ S(){ ps = this; } //~S(){} //(*) }; S makeS(){ return S{}; } int main(){ S…
Weijun Zhou
  • 746
  • 1
  • 7
  • 25
4
votes
1 answer

How does the 'explicit' keyword affect C++ copy constructors and function parameters?

The "explicit" keyword to modify the copy constructor can cause problems. Objects passed as function parameters are particularly susceptible to these issues. here are my codes: #include #include class Pig{ public: …
Andrés
  • 41
  • 2
4
votes
1 answer

Copy constructor implicitly called?

I have the following class with both a normal constructor and copy constructor defined. #include class Bla { public: Bla() { std::cout << "Normal Constructor Called\n"; } Bla(const Bla& other) { …
nick2225
  • 527
  • 5
  • 17
4
votes
1 answer

Can not knowing whether something is elided introduce undefined behavior?

Say we have a struct that has a member pointer that conditionally points to either an internal array, or to somewhere on the heap, like this: struct Ex { char* p; char data[14]; bool is_heap; Ex() : p(&data[0]),…
Jake Schmidt
  • 1,558
  • 9
  • 16
4
votes
3 answers

How to use copy elision when function is called in if block

In the following snippet, no move and no copy of A happens thanks to copy elision struct A; A function1(); A function2(); int main(int argc, char**) { if (argc > 3) { A a = function1(); } else { A a = function2(); } return…
pseyfert
  • 3,263
  • 3
  • 21
  • 47
4
votes
1 answer

Why does copy initialisation with braces elide copy/move construction?

Here is a C++ 14 program for comparing direct initialisation (no =) with copy initialisation (=):* #include struct A { A(int) { std::cout << "A(int)" << std::endl; } A(A&) { std::cout << "A(A&)" << std::endl; } A(A&&) {…
Géry Ogam
  • 6,336
  • 4
  • 38
  • 67
4
votes
3 answers

Unexpected copy constructor

In the following example I am expecting only a single copy-construction, as I thought the intermediate copies would by copy elided. The only required (I thought?) copy would be in the constructor of B to initialize the member variable a. #include…
Cory Kramer
  • 114,268
  • 16
  • 167
  • 218
4
votes
1 answer

Difference in Copy Elision for Trivial vs. Non-trivial Types

I'm inspecting copy-elision between trivial and non-trivial copy-able types when one function's return by value directly passes by value into another function. For the non-trivial case, it appears the object is directly transferred as expected, but…
4
votes
1 answer

Directly initializing non-copyable, non-movable members without using aggregate initialization

Background Suppose that I am trying to implement a fixed-size multi-dimensional array using a flat array: template struct multi_array { static constexpr std::size_t size() noexcept { return (Dims * ...…
4
votes
2 answers

Copy-elision of automatic variable for return

I am wondering if in C++0x "12.8 Copying and Moving class objects [class.copy] paragraph 31" when copy elision happens, exactly: When certain criteria are met, an implementation is allowed to omit the copy/move construction of a class object [...].…
towi
  • 21,587
  • 28
  • 106
  • 187
4
votes
1 answer

Is NRVO valid with exception throwing in body?

I am looking to understand the limitations of NRVO in C++. Would a function with an initial named declaration and a single return be optimised for NRVO and elide T val, even though the function myFunc() has a throwing potential? T myFunc(bool…
Doggiie
  • 95
  • 1
  • 1
  • 4
4
votes
1 answer

How to guarantee copy elision with std::variant?

I have this type: struct immobile { // other stuff omitted immobile(immobile&) = delete; immobile(immobile&&) = delete; }; immobile mk_immobile(); // e.g. this compiles // mk_immobile() is a prvalue and i is its result object immobile…
HTNW
  • 27,182
  • 1
  • 32
  • 60
4
votes
1 answer

C++17 copy elision and object destruction

From cppreference, When copy elision occurs, the implementation treats the source and target of the omitted copy/move (since C++11) operation as simply two different ways of referring to the same object, and the destruction of that object…
pterodragon
  • 429
  • 8
  • 16