I had this discussion with a colleague of mine on this. And would like to know the opinion of more folks as to which is "can" be more optimal? PS: If the code is just a hello world program, the -O3 results in identical code, but we are talking of a scenario where this code segment is in the middle of a large project.
2 Answers
Context would be of deciding importance. And your profiler would probably tell you to not sweat it.
In this case, a new std::string has to be constructed anyways, and the 'const reference to life-time-extended temporary value' would really only cause the compiler more work (to emit equivalent/identical code).
I'd opt for clarity:
Code intent, not method
So
std::string tmp("Hello");
Or
std::string tmp = "Hello";
would express the intent fully.
Comments
Chances are that the compiler will generate the same code, but using a reference is misleading to casual readers. Consider that instead of initializing it with a literal you used the return of a function:
std::string f();
std::string const & r = f(); // [1]
The line tagged as [1] seems to just be creating a reference (low cost operation) to an object managed somewhere else. The reader of the code will be left trying to figure out whether the referenced string can change externally or even if it might be destroyed leaving a dangling reference. They will have to go to the documentation of f() and find out that it is actually a temporary, and then back to the original code and figure out that this was just some programmer playing smart tricks.
On the other hand std::string s = f(); is much clearer on the intent: Whatever f() represents, a copy of that will be maintained in the local context. The object will not change externally and the lifetime is exactly the scope in which it is defined.
Note that in both cases the behavior is really the same, but in one case it is obvious to the casual reader, while in the other the reader must figure it out. I would use local objects in all cases where I can, and limit the lifetime extension to the few cases where the value won't cut it (which in real life I have only needed once).
10 Comments
std::string, then yes, the cost will be higher when returning by value. But if you are creating a std::string inside your function then you must return it by value. The extra copies will be elided (i.e. the string created inside the function and the returned string will be the same object) in most cases, and when that is not possible (and in C++11 only) the contents will be moved, which is a low cost operation. Consider for example operator+ when applied to strings, it returns by value.f(), but given an f() that does return by value, which option to use on the call site.
const char* a = "tmp";or evenchar a[] = "tmp";This could be faster ;)