我写了以下代码:
#include <iostream>
using namespace std;
int f()
{
cout << "f()" << endl;
return 3;
}
int v()
{
cout << "v()" << endl;
return 4;
}
int main()
{
int m = f(),v();
cout << m << endl;
return 0;
}
我希望它能打印出来:
f()
v()
3
使用g++ -O0 test.cpp -o test.out
进行编译并运行结果:
f()
3
为什么省略对v的调用? (这不能用于优化,因为我添加了标志-O0
)
答案 0 :(得分:21)
int m = f(),v();
该语句执行f()并将返回值赋给m,然后声明返回int类型的函数v()
。 int v();
也称为most vexing parse。
要完成comma operator
测试,请尝试:
int m;
m = f(),v();
cout << m << endl;
请参阅live sample。
答案 1 :(得分:4)
以下代码变体演示了这是做什么的:
#include <iostream>
int f() { std::cout << "f()" << std::endl; return 1; }
int main() {
int t = f(), v();
std::cout << t << std::endl;
return 0;
}
即使我们没有“v()”,这也会毫无错误地编译。
逗号运算符正在拆分此行
int t = f(), v();
到
int t = f();
int v();
第二行是一个函数原型,它声明会有一个函数int v()
,它不带参数并返回一个int。
它不会调用它,它只是预先声明它 - 如果编译器在实际定义之前遇到它的调用 - 因为body是一个空语句(;
)。编译器假定我们稍后或在不同的编译单元中实现它。
因为这通常会让经验和新程序员感到困惑,因为它是由C ++引入的,允许您将函数原型放在函数体内,这称为most vexing parse。