功能调用顺序

时间:2011-01-19 15:49:53

标签: c++ c

表达式

(func1() * func2()) + func3()

首先会对func1()* func2()进行求值,因为它有括号,或者可以按任何顺序调用函数,如

首先是func3()然后是(func1()* func2())

6 个答案:

答案 0 :(得分:13)

可以按任何顺序调用这些函数。

答案 1 :(得分:8)

运算符的优先级与操作数的评估顺序无关。

C或C ++标准不确定调用函数的顺序。

子表达式的评估顺序,包括

  • 函数调用的参数和
  • 运算符的操作数(例如, +, -, =, * , /),但以下情况除外:
    • 二进制逻辑运算符(&&||),
    • 三元条件运算符(?:)和
    • 逗号运算符(,

未指定

例如

  int Hello()
  {
       return printf("Hello"); /* printf() returns the number of 
                                  characters successfully printed by it
                               */
  }

  int World()
  {
       return printf("World !");
  }

  int main()
  {

      int a = Hello() + World(); //might print Hello World! or World! Hello
      /**             ^
                      | 
                Functions can be called in either order
      **/
      return 0;
  } 

答案 2 :(得分:6)

您无法对调用这些函数的顺序做出任何假设。编译器以任何顺序调用这些函数,将结果分配给临时函数,然后使用这些临时值来计算表达式的结果,这是完全有效的。

答案 3 :(得分:4)

可以按任何顺序进行这些调用。您想了解 C++ sequence points C++ sequence points

答案 4 :(得分:2)

很自然地认为在此psudocode A+B之前评估C

(A+b)*C

但事实并非如此。标准表示所有表达式的评估顺序是“未指定”,除非标准另有规定:

5/4 [expr]:

  

除非另有说明,否则顺序为   评估个人的操作   运算符和子表达式   个人表达和秩序   发生副作用的是   未指定的

然后,标准继续将带括号的表达式标识为“主要表达式”,但未指定主要表达式的评估顺序。 (5.1 / 5)。

在Standardese中,“未指定”并不意味着“未定义”。相反,它意味着“实施定义,但不需要文档。”因此,您甚至可能无法说出特定编译器的评估顺序。

这是一个简单的程序来说明行为:

#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");
}

在Win7上运行在Debug / x64上的MSVC10上,输出恰好是:

'C'(1)
'B'(2)
'A'(3)
'A+B'(4)
'A+B+C'(5)

答案 5 :(得分:1)

C / C ++中的括号强制操作顺序。 func1() * func2()将添加到func3(),但编译器可以选择在将结果传递给乘法/加法运算之前以任何顺序调用函数。