#include <stdio.h>
int main()
{
int y = 1;
if (y & (y = 2))
printf("true \n");
else
printf("false \n");
return 0;
}
输出:
true
在此程序中存在未定义的行为。输出始终为 true
。我尝试过几个编译器。谁能解释一下为什么是true
一直吗?
最佳答案
因为观察到的行为不是定义的行为。您使用的编译器似乎(仅通过观察)执行以下操作:
- 赋值
y = 2
- 步骤(1)的评估结果
- 评估
y
- 按位与上述步骤 (2) 和 (3) 的结果。
- 步骤 (4) 的评估结果
结果为(2 & 2)
,即true。问题是,1-2,然后3的顺序不是标准定义的。它也可以很容易是这样的:
- 评估
y
- 赋值
y = 2
- 步骤(2)的评估结果
- 按位与上述步骤 (1) 和 (3) 的结果。
- 步骤 (4) 的评估结果
结果将是(1 & 2)
,即假
或者它可能完全是别的东西。并非所有编译器都会执行第一个操作,并且您不能因为您使用的编译器执行该操作而假设它们全部都会执行此操作。您也不能假设因为他们这样做并且您观察到该行为,因此它是被定义的;事实并非如此。 编译器不定义行为;该标准确实如此,编译器有义务遵守。
注意:这个时代的定义存在漏洞,但它不是规范,甚至是标准松散定义的。您会发现标准中的某些区域表示某些内容是“实现定义的”。在这种情况下,标准相当清晰地指出了这些分歧领域。在这种情况下,您应该咨询您的实现以获得关于预期行为的明确结论,并在这样做时准备好接受一个简单的事实,即此类行为只能在实现的范围内依赖。这个(您的示例)不是这样的漏洞异常。
我的 clang 3.5 设备似乎(根据我的观察)运行第二个序列,而不是第一个序列,我可以走你的路并假设我尝试过的“所有”编译器(其中一个) )表现得像这样,因此它被定义为如此。我这样做是错误的,正如你的假设一样。
未定义的行为就是这样; 未定义。
关于c - 为什么 if 语句中未定义的行为为 true?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21351315/