当前时区为 UTC + 8 小时



发表新帖 回复这个主题  [ 4 篇帖子 ] 
作者 内容
1 楼 
 文章标题 : ^_^新手请教一个关于数组的问题
帖子发表于 : 2013-05-07 23:00 

注册: 2013-03-23 23:44
帖子: 2
系统: lubuntu
送出感谢: 0 次
接收感谢: 0 次
【问题描述】
如果连续声明两个数组a[n]和b[n],a[n]的地址和b[0]的地址一样了。
这样如果做一些输出,比如puts(a),就会把a和b都输出了。

【请问】
这是怎么回事?如何避免这样的问题?

【代码】
gcc 版本 4.6.3 (Ubuntu/Linaro 4.6.3-1ubuntu5)
代码:
#include<stdio.h>

main()
{
char a[5],b[5];

int i;
for (i = 0;i < 5;i++){
a[i]='a';
b[i]='b';
}

puts(a);

}

>输出:aaaaabbbbb

【By the way】
我是在我手机上用tcc编写c时发现这个问题的,tcc要颠倒声明顺序,先声明b数组,再声明a数组。
这样才能让b紧跟在a后,形成&a[5]与&b[0]相同。


望各位前辈指教,多谢了^_^


页首
 用户资料  
 
2 楼 
 文章标题 : Re: ^_^新手请教一个关于数组的问题
帖子发表于 : 2013-05-09 12:16 
头像

注册: 2007-08-07 18:14
帖子: 234
送出感谢: 4
接收感谢: 3
简直吐槽不能了

你这个问题是最基本的问题,你应该好好去看看书。看书,懂不。我要是你的老师一定罚你超书一百遍啊一百遍

建议好好读读 c++ primer Arrays and Pointers 这一章,一共就35页,俩小时也读完了。

好吧,简单说问题主要处在c++ 里面的字符数组本身不能当作字符串使用的,字符串必须使用'\0'结尾

puts 的参数是char * ,是要你输入一个字符数组型的字符串,不是仅仅是个字符数组就可以了。

使用不带'\0'的字符数组做字符串是危险的做法,会带来莫名其妙的bug.

你的程序可以这么改
代码:
...

for (i = 0;i < 4;i++)
{
    a[i]='a';
    b[i]='b';
}

a[4] = ‘\0’;
b[4] = '\0';
...


关于你说的那个a[n] 等于b的问题,本质上在于数组的名称实际存储的是数组的地址,a[5] 已经超出a这个数据的范围了,a后面你恰好定义的是b,所以取得了b这个数组。

当然理论上是这样,但是实际上的效果受很多因素的影响,尤其是编译器的优化和实现方式,比我我这里编译器自动做对齐,就不会出现你的这个现象。你可以用printf打印&a[5]和&b看看地址就好了。

但总之要记住的是使用超出地址范围的数组元素是灰常危险的用法,是各种莫名其妙的问题的根源之一。


_________________
什么是历史?历史是魔术师箱子里那只变来变去的小白鸽;
什么是真相,真相只是观众最愿意看到的硬币的那一面。


页首
 用户资料  
 
3 楼 
 文章标题 : Re: ^_^新手请教一个关于数组的问题
帖子发表于 : 2013-05-09 15:47 
头像

注册: 2006-03-14 10:25
帖子: 644
送出感谢: 1
接收感谢: 4
楼上多点宽容么,谁都从新手过来的。
基本上楼主需要看看c语言下字符串的定义和使用。


页首
 用户资料  
 
4 楼 
 文章标题 : Re: ^_^新手请教一个关于数组的问题
帖子发表于 : 2013-05-11 8:16 

注册: 2013-03-23 23:44
帖子: 2
系统: lubuntu
送出感谢: 0 次
接收感谢: 0 次
多谢指教!


页首
 用户资料  
 
显示帖子 :  排序  
发表新帖 回复这个主题  [ 4 篇帖子 ] 

当前时区为 UTC + 8 小时


在线用户

正在浏览此版面的用户:没有注册用户 和 2 位游客


不能 在这个版面发表主题
不能 在这个版面回复主题
不能 在这个版面编辑帖子
不能 在这个版面删除帖子
不能 在这个版面提交附件

前往 :  
本站点为公益性站点,用于推广开源自由软件,由 DiaHosting VPSBudgetVM VPS 提供服务。
我们认为:软件应可免费取得,软件工具在各种语言环境下皆可使用,且不会有任何功能上的差异;
人们应有定制和修改软件的自由,且方式不受限制,只要他们自认为合适。

Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
简体中文语系由 王笑宇 翻译