c++中的点运算符求值顺序

dot operator order of evaluation in c++

本文关键字:顺序 运算符 点运算 c++      更新时间:2023-10-16

我正在读《C++初级读本(第5版)》,我遇到了一些我不确定是否正确理解的问题。

这个例子与他们在书中给出的例子非常相似。假设我们有一个返回字符串的函数(或任何具有非静态成员的类):

string some_function(par1, par2) {
     string str;
     // some code
     return str;
}

我知道你可以使用任何函数的返回值来访问它的成员,即这样的东西是有效的:

auto size = some_function(arg1, arg2).size(); // or whatever member of class

然而,由于点运算符.和函数调用运算符()具有从左到右的分组和相同的优先级,因此上面的表达式应该是这样的:

(some_function(arg1, arg2)).size()

我想到目前为止我是对的吧?我不明白的是评估的顺序。由于没有为.运算符指定求值顺序,这意味着将首先对some_function(arg1, arg2)size()求值。但是,如果它不知道在哪个对象上工作,它如何首先评估size()?这意味着评估的顺序应该从左到右固定,但事实并非如此。这怎么可能?

另一个例子是这样的:

 cin.get().get();

同样,第一个cin.get()似乎应该在第二个get()之前求值,因为它不知道它在哪个对象上工作,但情况似乎并不一定如此。

具有相同优先级的运算符将根据其关联性进行评估,您可以正确地观察到,对于包含函数调用和元素选择运算符的运算符组,从左到右都是关联性。因此,是的,给定表达式

x = foo().bar();

操作顺序为

x = (((foo()).bar)());

说明所有相关运算符的相对优先级和关联性。不过,没有人以这种方式编写代码。

同样,给定

cin.get().get()

操作顺序是

(((cin.get)()).get)()

,所以是的,优先级规则导致首先对cin.get()子表达式进行求值,从而产生应用第二个.(以及表达式的其余部分)的对象。