c - c 如何计算包含前缀增量的表达式?

标签 c evaluation prefix-operator

假设在执行左侧每个语句之前 x 被初始化为 0,则结​​果就是右侧显示的值:

(++x + ++x) + ++x == 7
++x + (++x + ++x) == 9
++x + ++x + ++x   == 7

为什么第一个语句的结果是 7 而第二个语句的结果是 9 ???

为什么第一条语句的结果和第三条语句的结果一样???

最佳答案

这是未定义的行为...编译器很可能会编写如下所示的代码。

(++x + ++x) + ++x == 7
x = 0
x++ => 1 (x)
x++ => 2 (x)
r = 2 + 2
x++ => 3 (x)
r + x = 7

还有这个

++x + (++x + ++x) == 9

x++ => 1  x + (++x + ++x)
x++ => 2  x + (x + ++x)
x++ => 3  x + (x + x)
//You'll have x + (x + x) where x is 3
// Now
r = 3 + 3
x + r = 9

请注意,所有这些对于您当前使用的编译器都有效。其他编译器可能足够聪明,可以返回与某些编译器不同的相同结果。它甚至可能取决于优化级别,并且这一切都取决于未定义的行为。

总之,不要编写如下所示的代码。我很确定您的编译器正在输出一些关于此的警告。

进一步解释一下发生的情况是您正在就地修改寄存器。在它可以执行操作之前,它必须评估“++”。所以人们可能会认为你最终会得到:

1 + 2 + 3 => 5

但实际上,由于++ 不应该分配新内存,因此它会增加原值。可以使用括号强制从左到右的顺序。因此,在一种情况下,当对 r + x 求和时,它会增加 2 倍,然后增加第三次,带括号的版本会强制每个 ++ 从左到右,然后求和x + r。但因为它是未定义的行为。这其实没什么意义。只是不要这样做。

关于c - c 如何计算包含前缀增量的表达式?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22116802/

相关文章:

.net - .NET 运行时是否在内部映射到 win32 函数调用?

c++ - 什么样的 .lib 文件以 "!<arch>"开头?

javascript - i-- 和 i = i-1 的评估不一样

C++ 表达式值(运算符优先级)

c - 如何在 delphi 中创建文件并将其传递给 C DLL 并在回调中使用该文件?

c - c函数中的指针 "value computed is not used"

c++ - 在 C++ 中同时进行赋值和条件测试

haskell - haskell 中列表的强制严格性

c - C 中前缀递增和后缀递增之间的差异(++a 和 a++)