2013-04-15 181 views
6
#include <stdio.h> 
int a[100]; 
int main(){ 
    printf("%d",a[5]); 
    return 0; 
} 

上面的代码总是打印'0'还是编译器特定?我使用的是gcc编译器,输出为'0'。C中的全局变量是否始终初始化为零?

+0

有什么阻止您将变量初始化为您想要的值? –

回答

18

是的,a所有成员都保证被初始化为0。

从C89的部分3.5.7标准

如果具有静态存储持续时间的对象没有被初始化 明确,它被隐含地初始化,好像每个具有 算术类型的成员都被赋值为0,并且具有指针类型 的每个成员都被赋值为空指针常量。

+0

我相信这是来自“X3”ANSI C草案? C标准中仍然保留了相同的文本,但为什么引用这样一个陈旧的来源? – Lundin

+0

@Lundin这是我不得不将到手的唯一来源,我认为它仍然比“是的,(未引用的)标准是这么说的”更好的答案做。我已经为您提供了更现代化的标准。 – simonc

+2

啊哈,井[C11草案(http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf)是很容易在网络上找到。草案和最终的C11标准之间的区别是化妆品,除了[小勘误](http://stackoverflow.com/questions/13914050/what-is-c11-cor-12012/13914051#13914051)。 – Lundin

3

是的。 任何全局变量都被初始化为该类型的默认值0是默认值,并自动转换为任何类型。 如果它是一个指针,0成为NULL

全局变量那里在归零的数据段空间。

它是不是编译器特定但在C标准中定义。

因此它总是会打印0.

+0

XORing与它本身是一个实施细节;这并不重要*这些东西是如何归零的。 – glglgl

+0

@glglgl谢谢... :) – Sam

+3

此外,我很怀疑,任何现代化的实现使用XOR空记忆,因为它会产生额外的读操作,这是完全不必要的,增加了应用程序的启动时间。对于没有特殊指令的“将寄存器设置为零”的某些处理器,清除寄存器对于自己进行异或操作非常有效。将内存区域设置为零并不好。 –

0

它不是编译器特定的。该代码将始终打印0

1

C中的全局变量总是初始化为零吗?

是和它在C标准中定义。

2

声明的文件范围对象没有显式初始化符,默认情况下由0初始化(并且指向NULL)。

在没有显式初始化的情况下声明的块范围内的非静态对象未初始化。

7

“全局变量”定义在文件范围之外,任何函数之外。在文件范围内定义的所有变量以及使用关键字static声明的所有变量都有一些名为的静态存储持续时间。这意味着它们将被分配在记忆的一个单独部分中,并在整个程序生命周期中存在。

这也意味着它们保证在任何C编译器上被初始化为零。

从目前的C标准C11 6.7.9/10:

” ...如果具有静态或线程存储持续时间的对象没有初始化 明确,则:

- 如果它有指针类型,它被初始化为空指针;

- 如果有算术类型,它被初始化为(正或无符号)为零;”

实际上,这意味着如果你初始化的全局变量给定值,就会有一个价值它将被分配到一个通常被称为.data的内存段中,如果你没有给它赋值,它将被分配到另一个段.bss中,全局永远不会被分配到堆栈上