【发布时间】:2011-04-16 15:31:27
【问题描述】:
在 C 中,当左侧操作数为负值时,按位左移操作调用未定义行为。
来自 ISO C99 (6.5.7/4) 的相关引用
E1 E2,减少模 比结果类型中可表示的最大值大一。如果 E1 有一个签名 类型和非负值,并且 E1 × 2E2 在结果类型中是可表示的,那么就是 结果值;否则,行为未定义。
但在 C++ 中,行为是明确定义的。
ISO C++-03 (5.8/2)
E1
意思是
int a = -1, b=2, c;
c= a << b ;
在 C 中调用未定义行为,但该行为在 C++ 中已明确定义。
是什么迫使 ISO C++ 委员会认为这种行为与 C 中的行为相反?
另一方面,当左操作数为负时,按位右移操作的行为是implementation defined,对吧?
我的问题是为什么左移操作调用 C 中的未定义行为,为什么右移操作符只调用实现定义的行为?
P.S:请不要给出“这是未定义的行为,因为标准是这样说的”这样的答案。 :P
【问题讨论】:
-
C 和 C++ 是由不同委员会标准化的不同语言。我看不出有什么令人惊讶的地方。
-
此外,C++ 基于 C89/C90。 C 委员会随后朝着 C99 的不同方向发展。 C99 和 C++ 都基于原始的 C 标准,但分歧根本不协调。
-
您的 C++ 引用仅定义类型为无符号时的行为。您是否忘记复制有关带符号值的段落?
-
@R.. 文本定义了第一句签名的行为。然后,它进一步详细说明了其他句子中未签名的行为。
-
我看到早期的标准有这种差异,但 C99 和 C++11 标准对于有符号和无符号整数类型的左移和右移都要求相同的行为。
标签: c++ c language-lawyer undefined-behavior bit-shift