在C循环(铿锵VS海湾合作委员会)的数组值
问题描述:
我试图在c中的for循环播放数组初始化。在C循环(铿锵VS海湾合作委员会)的数组值
这里是我试过的程序:
#include<stdio.h>
int main(){
for(int i=0;i<3;i++){
for(int j=0;j<3;j++){
int br[10]={0};
printf("%d\n", br[-1]);
}
}
return 0;
}
这段代码的结果时,用gcc编译如下:
0 1 2 0 1 2 0 1 2
时铿锵编译同样的程序,结果是:
0 0 0 0 0 0 0 0 0
如果我通过在开始第二个lo之前进行数组初始化来调整程序OP:
#include<stdio.h>
int main(){
for(int i=0;i<3;i++){
int ar[10]={0};
for(int j=0;j<3;j++){
int br[10]={0};
printf("%d\n", br[-1]);
}
}
return 0;
}
我得到的输出0 0 0 0 0 0 0 0 0
对GCC和铛
谁能解释究竟是什么在这里发生的事情,当我尝试,为什么这些结果显示了这两个不同的访问负指数编译器(gcc和clang)以及为什么在第二次循环改变所有内容之前另一个数组初始化。
答
br[-1]
的行为是undefined。
C标准没有定义试图将边界阵列的外部访问的元素的行为。 (有趣的是,主要是因为这个原因,为什么C被许多人视为一种“不安全”的语言)。您可以随时检查生成的汇编程序,以便全面分析编译器生成的内容。
答
Here is an example of using negative array idexes.
如果使用BR [-1]您在阵列之前打印元素:
some stuff | your array | more stuff
X X X X X | 0 0 0 0 ...| X X X X
^this element will be printed
因此,在一个情况下,你也许有i或j的值,但在此之前数你的数组可以用不同的编译器或编译器选项来改变。
@Bathsheba 在我的链接最多的回答说,行为是C99§6.5.2.1/ 2定义的,但你不知道哪个变量位于您的阵列前方。
下标运算符[]的定义是E1 [E2]等于(*((E1)+(E2)))。
'BR [-1]'是[未定义行为(https://en.wikipedia.org/wiki/Undefined_behavior)......这就是 – LPs
我不这么认为。我认为这与内存分配有关。 – satishdd
不,它是UB,纯粹而简单。编译器保留吃你的猫的权利。 – Bathsheba