It is natural to think that A+B evaluates to C in this psudocode:
(A+b)*C
But actually it is not. The Standard states that the evaluation order for all “Unspecified” expressions, unless otherwise specified in the Standard:
5/4 [expr]:
Except where noted, the order of evaluation of the operands of individual operators and subexpressions of individual expressions and the order in which side effects occur is not defined
Then, the expression in parentheses is identified as “primary expression” in the standard, but the evaluation order for primary expressions is not specified. (5.1 / 5).
In the standard, "Unspecified" does not mean "Undefined". Rather, it means "Implementation is defined, but documentation is not required." That way, you won’t even be able to tell which evaluation order is for a particular compiler.
Here is a simple program illustrating the behavior:
#include <iostream> #include <string> using namespace std; class Foo { public: Foo(const string& name) : name_(name) {++i_; cout << "'" << name << "'(" << i_ << ")\n"; }; operator unsigned() const { return i_; } Foo operator+(const Foo& rhs) const { string new_name = name_; new_name += "+"; new_name += rhs.name_; return Foo(new_name); } private: string name_; static unsigned i_; }; unsigned Foo::i_ = 0; int main() { (Foo("A") + Foo("B")) + Foo("C"); }
On my MSVC10 running in Debug / x64 on Win7, the output was as follows:
'C'(1) 'B'(2) 'A'(3) 'A+B'(4) 'A+B+C'(5)
John dibling
source share