在C 11中是左移(<<)负整数未定义的行为吗?

在C 11中是左移(<<)负整数未定义的行为吗?,第1张

概述在C 11中左移一个负的int未定义行为? 相关的标准段落是5.8: 2/The value of E1 << E2 is E1 left-shifted E2 bit positions; vacated bits are zero-filled. If E1 has an unsigned type, the value of the result is E1 × 2E2, reduced m 在C 11中左移一个负的int未定义行为?

相关的标准段落是5.8:

2/The value of E1 << E2 is E1 left-shifted E2 bit positions; vacated
bits are zero-filled. If E1 has an unsigned type,the value of the
result is E1 × 2E2,reduced modulo one more than the maximum value
representable in the result type. Otherwise,if E1 has a signed type
and non-negative value,and E1×2E2 is representable in the result
type,then that is the resulting value; otherwise,the behavior is
undefined.

令我困惑的部分是:

Otherwise,if E1 has a signed type and non-negative value,and E1×2E2
is representable in the result type,then that is the resulting value;
otherwise,the behavior is undefined.

这应该被解释为意味着左移任何负数是UB吗?或者这只是意味着如果你的LS是负面的,结果不符合结果类型,那么它是UB?

此外,前面的条款说:

1/The shift operators << and >> group left-to-right.
shift-Expression:
additive-Expression
shift-Expression << additive-Expression
shift-Expression >> additive-Expression

The operands shall be of integral or unscoped enumeration type and
integral promotions are performed.

The type of the result is that of the promoted left operand. The
behavior is undefined if the right operand is negative,or greater
than or equal to the length in bits of the promoted left operand.

这使得显式地使用一个 *** 作数的负数为UB.如果是UB对另一个 *** 作数使用负数,我希望在这里也明确.

所以,底线是:

-1 << 1

未定义行为?

@Angew provided对标准版的一个psudocode解释,简洁地表达了一个可能的(可能)有效的解释.其他人质疑这个问题是否真的关于语言“行为是不确定”的适用性,而不是我们(StackOverflow)使用短语“未定义的行为”.这个编辑是为了进一步澄清我正在试图问的内容.

@ Angew对Standardese的解释是:

if (typeof(E1) == unsigned integral)  value = E1 * 2^E2 % blah blah;else if (typeof(E1) == signed integral && E1 >= 0 && representable(E1 * 2^E2))  value = E1 * 2^E2;else  value = undefined;

这个问题真的归结于这一点 – 实际上是正确的解释:

value = E1 left-shift-by (E2)switch (typeof(E1)){case unsigned integral :  value = E1 * 2^E2 % blah blah;  break;case signed integral :  if (E1 >= 0)  {     if (representable(E1 * 2^E2))    {      value = E1 * 2^E2;    }    else    {      value = undefined;    }  }  break;}

SIDenote在看着这个psudocode这一点使我很清楚,@ Agnew的解释是正确的.

解决方法 是的,我会说这是未定义的.如果我们将standardese翻译成伪代码:
if (typeof(E1) == unsigned integral)  value = E1 * 2^E2 % blah blah;else if (typeof(E1) == signed integral && E1 >= 0 && representable(E1 * 2^E2))  value = E1 * 2^E2;else  value = undefined;

我会说出他们对右手 *** 纵的明确原因,而不是左手 *** 纵的原因是你所引用的paragrpah(右手 *** 纵的情况)适用于左转和右转.

对于左手 *** 纵,裁决不一致.左移一个负数是未定义的,右移它是实现定义的.

总结

以上是内存溢出为你收集整理的在C 11中是左移(<<)负整数未定义的行为吗?全部内容,希望文章能够帮你解决在C 11中是左移(<<)负整数未定义的行为吗?所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/langs/1248826.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-06-07
下一篇 2022-06-07

发表评论

登录后才能评论

评论列表(0条)

保存