【问题标题】:dot operator order of evaluation in c++c++中的点运算符求值顺序
【发布时间】:2014-12-11 21:31:38
【问题描述】:

我正在阅读“C++ Primer(第 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() 之前评估,因为它不知道它在哪个对象上工作,但这似乎不一定是这种情况。

【问题讨论】:

    标签: c++ operators operator-precedence


    【解决方案1】:

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

    x = foo().bar();
    

    操作顺序是

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

    考虑所有涉及的运算符的相对优先级和关联性。但是,没有人以这种方式编写代码。

    同样,给定

    cin.get().get()
    

    操作顺序是

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

    ,所以是的,优先规则导致首先计算 cin.get() 子表达式,产生应用第二个 .(然后是表达式的其余部分)的对象。

    【讨论】:

    • 好吧,也许我没有说对,但优先级和关联性不应该只说明运算符的操作数是如何分组的吗?但是,评估的顺序可能不同,例如:a * b + c = (a * b) + c 可以通过首先评估 a,然后是 b,将它们相乘,然后评估 c 并将其添加到 a 的结果来评估和 b,或者它可以评估 c,然后是 b 和 a,或者介于两者之间的任何东西。那么它如何与点运算符一起使用?例如 cin.get().get()
    • @Murdac: getget() 是两个不同的东西:第一个只是用来确定使用什么方法,第二个是它的应用。所以就点运算符而言,这两位是对象&使用什么方法;一旦评估了点,您就有了一个可以执行的可调用对象(该特定对象的方法)。
    • @Scott Hunter:我想我明白了,我实际上误解了运算符的含义。它实际上意味着“从左侧的对象中获取名为 foo 的成员”,这意味着它首先评估对象或成员的名称,这最终允许给定的结构。非常感谢。
    • 这是一个有趣的问题,你看到它并首先认为它很明显,但随后意识到它非常微妙。
    • 是的,我不得不考虑一下我的答案。这个问题围绕着每个运算符的操作数是什么的问题。我曾希望我的答案中的分组括号能澄清问题的这一方面,但我想它们还不够。感谢@ScottHunter 的协助。
    猜你喜欢
    • 2021-07-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-01-07
    • 2015-03-12
    • 2010-11-29
    • 2011-11-03
    • 2021-08-23
    相关资源
    最近更新 更多