算术赋值运算符 - 左侧仅计算一次 [英] Arithmetic assignment operator - left side evaluated only once

查看:27
本文介绍了算术赋值运算符 - 左侧仅计算一次的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

正如标题所说,我在一些 C 讲义中发现了这样一句话.

As the title says I found such a sentence in some C lecture notes.

我想不出任何例子来证明这句话.

I can't invent any example proving that sentence.

在我看来,每个赋值操作都被评估一次,因为当我们希望它被评估多次时,我们会放入一个循环中.那我错过了什么?

In my opinion every of assignment operations is evaluated once, because when we want it to be evaluated more than once we put in in a loop. What am I missing then?

我已经搜索过,但在 SO 上找不到答案.

I've searched but couldn't find an answer here on SO.

推荐答案

C 说:

(C99, 6.5.16.2p3) E1 op= E2 形式的复合赋值与简单赋值表达式 E1 = E1 op (E2) 的不同之处仅在于左值 E1 只计算一次."

(C99, 6.5.16.2p3) "A compound assignment of the form E1 op= E2 differs from the simple assignment expression E1 = E1 op (E2) only in that the lvalue E1 is evaluated only once."

以下是其重要性的一些示例:

Below are some examples of why it matters:

示例 1:

 a[i++] += 1;

等同于:

 a[i] = a[i] + 1; i++;

因为 += 的左操作数被评估一次.

because the left operand of += is evaluated once.

如果它没有被评估一次,它将与:

If it was not evaluated once it would be the same as:

a[i++] = a[i++] + 1;

这当然是不同的(顺便说一句,还有未定义的行为).

which is of course different (and undefined behavior BTW).

示例 2:

*foo() += 1;

假设 foo 在这里返回一个指向标量类型对象的指针并产生副作用(例如它在终端上打印一个字符串).使用复合赋值运算符,它只会打印一次字符串,而不是两次.

assuming foo here returns a pointer to an object of a scalar type and produces side effects (for example it prints a string on the terminal). With the compound assignment operator it will print the string only once and not two times.

示例 3:

REG |= 0x01;

假设 REG 这里是一个 IO 寄存器(类似于 #define REG (*(volatile uint8_t *) 0x42))并且每次读取这个特定的 IO 寄存器都会触发硬件事件.使用复合赋值运算符只会读取寄存器一次,而不是两次.

assuming REG here is an IO register (something like #define REG (*(volatile uint8_t *) 0x42)) and that every read to this specific IO register triggers a hardware event. The register will be read only once with the compound assignment operator and not two times.

EDIT:按照 @R. 评论我击中了示例 3.我认为最编译器不会在此表达式中执行读取:REG = 31 或使用此表达式执行两次读取:REG = REG |0x01.

EDIT: following @R. comment I striked the example 3. I think most compilers do not perform a read in this expression: REG = 31 or two reads with this expression: REG = REG | 0x01.

这篇关于算术赋值运算符 - 左侧仅计算一次的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆