【问题标题】:What is short-circuit evaluation in C?C上的短路评估
【发布时间】:2021-11-21 06:03:33
【问题描述】:

我正在从 Kelley-Pohl 的 A Book on C 中学习 C,并且有一个我不明白的练习:

int a = 0, b = 0, x;

x = 0 && (a = b = 777);
printf("%d %d %d\n", a, b, x);
x = 777 || (a = ++b);
printf("%d %d %d\n", a, b, x);

他们只是说想象输出并将其与真实输出进行比较。我以为输出会是

777 777 0

778 778 1

但它是

0 0 0

0 0 1

【问题讨论】:

标签: c operators logical-operators short-circuiting


【解决方案1】:

&& 运算符使用lazy evaluation。如果&& 运算符的任一侧为false,则整个表达式为false

C 检查运算符左侧的真值,在您的情况下为0。由于 0 在 c 中为 false,因此永远不会计算操作的右侧表达式 (a = b = 777)

第二种情况类似,只是如果左侧表达式返回true|| 返回true。还要记住,在 c 中,任何不是0 的东西都被认为是true

希望这会有所帮助。

【讨论】:

  • 要记住的其他关键事项是赋值的优先级非常低(只有逗号运算符较低)并且a || b 的计算结果为01
【解决方案2】:

来自 C 标准(6.5.13 逻辑与运算符)

3 如果两个操作数比较,&& 运算符应产生 1 不等于0;否则,它产生 0。结果的类型为 int。

4 与按位二进制 & 运算符不同,&& 运算符保证 从左到右的评估;如果计算第二个操作数,则有 第一个和第二个评估之间的序列点 操作数。 如果第一个操作数比较等于 0,则第二个 不计算操作数。

在这个表达式语句中

x = 0 && (a = b = 777);

第一个操作数比较等于 0。所以第二个操作数没有被计算,即变量 ab 的值没有改变。所以变量x将根据该部分的第3段设置为0

来自 C 标准(6.5.14 逻辑或运算符)

3 ||如果其任一操作数比较,运算符 将产生 1 不等于0;否则,它产生 0。 结果的类型为 int。

4 不同于按位 |运算符,||运营商保证 从左到右的评估;如果计算第二个操作数,则有 第一个和第二个评估之间的序列点 操作数。 If 第一个操作数比较不等于 0,第二个 不计算操作数。

在这个表达式语句中

x = 777 || (a = ++b);

第一个操作数比较不等于 0。所以第二个操作数没有被计算,即变量 ab 的值没有改变。所以变量 x 将被设置为 1根据该部分的第 3 段。

如果你要改变表达式中操作数的顺序,比如

x = (a = b = 777) && 0;
x = (a = ++b) || 777;

您会得到预期的结果。

【讨论】:

    猜你喜欢
    • 2012-02-10
    • 2017-09-10
    • 1970-01-01
    • 1970-01-01
    • 2015-12-01
    • 2015-11-14
    • 2017-01-21
    • 2010-12-21
    相关资源
    最近更新 更多