c++ - C 数组的初始化问题 ?
大家讲道理
大家讲道理 2017-04-17 11:11:15
[C++讨论组]

今天看了一个代码:

int main(){
  char buff[10];
   printf("%d\n", buff[2]);   // 输出一些随机的数字或字符
   return(0);
}

我也很久没接触C了,和我印象中C数组的声明有些不一样。我记得数组需要一些初始化的,类似 char buff[10] = {0}; 或者 static char buff[10];。为何上面的数组不需要初始化??还是我本来就记错了??

是不是当char buff[10]的时候,已经在内存中的什么地方为这个数组分配了空间??当我用gdb调试的时候,print buff,会输出_\000%\000\000\000\000?\177

谢谢解疑。

大家讲道理
大家讲道理

光阴似箭催人老,日月如移越少年。

全部回复(3)
黄舟

“初始化”这个术语确实有些误导。不能顾名思义。数组的所谓“初始化”并非是“给数组分配内存”,而仅仅是“归零数组”。

char *string[10] 这样的语句,就已经声明了数组,并分配了储存空间。储存空间是在栈上静态分配的。这时数组是可以使用的。

但由于每一个程序分配到的内存都是“二手”的,里面可能有上一个程序保存的数据,因此这时,数组中的内容是随机内容。因此,我们需要对数组进行归零。这就叫数组的初始化


对于数组的归零,有三种方式。考虑 int a[10] 这个数组:

  1. 手工用 a[0] = 0; a[1] = 0; a[2] = 0…… 这样的语句

    这种做法是非常可笑的,效率低,容易出错,不应该使用。

  2. 使用循环 for (i = 0; i < 10; i++) a[i] = 0;

    这种做法本质上是和方法 1 相同的。效率很低,容易出错。不过 gcc 等高级编译器可以优化成 memset(),因此一定要使用一款好的编译器。微软的编译器就不多说了。

  3. memset(a, 0, 10)

    不错的方法,这种方法使用的很广泛。但由于不是声明时就初始化,比较繁琐。

  4. int a[10] = {0};

    好方法。这在声明时就给数组指定了全部是 0 的内容。

    有人要问了,哪里有这样的?难道不是:int a[10] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; 吗?实际上,只写一个 0 是一种简便写法,所有元素都会被设置成 0,一目了然。


不同的编译器,或同款编译器在不同的编译选项下,可能会把数组自动清零。这种情况下,容易遗忘初始化数组。要小心 Debug 模式没问题,Release 模式有问题的陷阱。

不过,如果你能保证,你访问的数组内容之前,已经向数组保存了有意义的数据,比如在使用 a[0] 之前已经 a[0] = 2 了,那么是没有任何问题的。

通常来说,没事就给所有的元素都初始化一下是完全没必要的。比如:

char str[10] = {'\0'};
scanf("%s", &s);

是完全没必要的。char str[10] = {'\0'}; 完全可以改成 char str[10];

迷茫

局部变量的空间分配在栈上;没有初始化的时候,取决于编译器的实现,一般不应该做任何假定。

伊谢尔伦

C/C++中除了全局变量都不会进行初始化。需要程序员自己初始化,也就是像楼主说的那样。 这个程序故意对没有初始化的数组读取。是不规范的代码

热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习
PHP中文网抖音号
发现有趣的

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号