(This question is inspired by Nicolai Josuttis' CppCon 2017 talk.)
Consider the following source file (for an object, not a complete program):
#include <string>
class C {
std::string s_;
public:
C(std::string s) : s_(s) { };
void bar();
};
void foo() {
std::string hello { "The quick brown fox jumped over the lazy dog" };
C c { hello };
c.bar();
}
And its compilation result on GodBolt.
Even with the -O2
(and even with -O3
) it seems a string constructor is called three times. Specifically, s
is constructed, used only to construct s_
, then destructed. My questions:
- Is the compiler allowed to simply construct
s_
from the arguments to the ctor, not constructings
at all? - If not, is the compiler allowed to move-construct
s_
froms
, seeing how the latter is unused? - If any of the previous answers is "yes" - why aren't gcc and clang doing so?
- If
s
is properly constructed, can't the compiler avoid the construction ofhello
, seeing how it has no other use? Or at least move from it?