数组索引中的序列点

时间:2016-05-24 02:17:11

标签: c

我制作了这段代码

#include <stdio.h>

int main(void)
{
    int i = 0;
    int arr[20];
    while(i < 20)
    {
         arr[i++] = i;
         printf("%d\n", arr[i-1]);
    }
    return 0;
}

似乎打印出预期的结果,为什么说你可以有未定义的行为?

3 个答案:

答案 0 :(得分:2)

您正在调用undefined behavior。您已使用sequence points,其使用在C中未定义。

你说似乎打印出预期的结果 - 可能可能,因为它未定义。因此,您获得预期值的事实只是纯粹的运气。

至于获得一些警告,请编译并运行代码;它确实会给你一个警告:

  

警告:'i'上的操作可能未定义[-Wsequence-point]

现场演示here

此外,如果您在考虑为什么它只是一个警告而不是错误,那么请注意编译器绝不一定要报告所有的未定义的行为 - 它的工作只是编译你的代码,而不是指出你未定义的行为。

答案 1 :(得分:1)

根据评估顺序,第一次执行

     arr[i++] = i;

可能最终将arr[1]设置为1(如果首先评估LHS)或0(如果首先评估RHS)。如果它们并行执行,结果可能是任何结果。

我们无法保证该行之后的程序状态。不要使用它。

答案 2 :(得分:1)

&#34;它按预期工作&#34;是未定义行为的可能结果之一。

arr[i++] = i; 显式被称为语言标准中未定义行为的示例。评估每个子表达式的顺序是未指定的;它不能保证从左到右。对于i == 1以下结果中的任何都是可能的:

arr[1] = 1;
arr[1] = 2; 
arr[2] = 2; 
arr[2] = 1;