Function return without assignment

Started by
3 comments, last by Aardvajk 17 years, 5 months ago
If you have a function that returns some object, but the caller doesn't assign it to anything, will the compiler know so that it treats it as if the function doesn't return anything? For example:

LargeObj Function()
{
  //do something
  return( LarObj );
}

void main()
{
  Function();
}

Advertisement
To my knowledge there is nothing in the c++ standard that says the compiler has to optimize away the return value and so the only way to know would be to examine the assembly produced by the compiler, but ofcourse that would very with compiler so in short id say it may or may not :-).
The compiler will still compile the function to return the value at the end. The only difference is that the value is left in the register and nothing happens to it once the program counter returns to the caller routine. Thus, it will get overwritten and lost.

If the caller assigns it to a variable, then there will be instructions to copy the value left in the return register to the stackframe.

Thus, it is of no real consequence really. If you know you're never gonna use the return, and you wanna save up on that "move to register" clock cycle, just make the function void.
The compiler cannot optimize away the return statement inside the function body itself, because it has no way of knowing that the return value is not used in *any* call to the function in *any* translation unit. However, if the compiler decides to inline the function at a given call site, the inlined copy will probably be subsequently optimized away.
Also bear in mind that something of significance may happen in the object's constructor that needs to execute regardless of whether the object is assigned after the function exits.

class x{public:    x(){ std::cout << "x created\n"; }};x f(){    return x();}int main(){    f();    return 0;}


You would expect this program to print "x created", and indeed it does with both Borland BCC55 and Digital Mars C++ compilers. In a less contrived example, a program could behave significantly differently if the creation of the object was optimised away.

It would be expecting a lot from a compiler to be able to "know" whether or not it was safe to perform this optimisation.

One area where a similar optimisation is common though is when an object is assigned. Consider the following:

class x{public:    x(){ std::cout << "constructor\n"; }    x(const x &v){ std::cout << "copy\n"; }};x f(){    x a; return a;}int main(){    x a=f();    return 0;}


If the above is compiled with Borland BCC55 (without optimisation), it outputs:

constructorcopy


but with Digital Mars C++

constructor


since DMC is by default optimising away the creation then the copy. While these optimisations are very clever and helpful, it is best not to rely upon them from compiler to compiler.

This topic is closed to new replies.

Advertisement