Chinaunix首页 | 论坛 | 博客
  • 博客访问: 4207391
  • 博文数量: 176
  • 博客积分: 10059
  • 博客等级: 上将
  • 技术积分: 4681
  • 用 户 组: 普通用户
  • 注册时间: 2006-03-24 12:27
文章分类

全部博文(176)

文章存档

2012年(1)

2011年(4)

2010年(14)

2009年(71)

2008年(103)

分类: C/C++

2008-11-29 00:23:25

By zieckey (http://blog.chinaunix.net/u/16292/index.html)

请写出下面一个简单程序的输出结果。

#include

#include

int main()

{

     char array1[7] = {'a', 'b', 'c'};

     char array2[3] = {'e', 'f', 'g'};

     printf( "strlen(array1)=%d\n", strlen( array1 ) );

     printf( "strlen(array2)=%d\n", strlen( array2 ) );

     return 0;

}

关键问题就是弄懂字符串数组的初始化和strlen函数的计算过程。

 

首先,strlen函数在计算字符数组长度时,它会遍历待检测字符数组的所有字符,直到遇到一个null字符,才会停止,而字符串数组在初始化过程中会在结尾加上一个'\0'字符,null字符,当然前提是字符串数组有多余的位置留给null字符。


让我们再看array1array2array1定义的长度为7,初始化时只赋了3个值,故有空余的空间留给null字符,故初始化时会在字符串末尾添加null终结字符,对于array2 来说,定义的长度为3,赋了3个值,没有空余的空间留给null字符,所有strlen在检查完array2,继续检查array2所在内存地址后的内存,直到遇到一个null字符才停止,所以几乎不可能会得出3


局部变量在内存中的存储是以压栈的方式存储的(这是众所周知的,局部变量是存储在栈中),栈地址是由高到低方向增长,即先定义的变量在高地址,后定义的变量在低地址.

array2的首地址接着array1的尾地址,但从VC的编译器的角度来看,操作系统是32位的,内存地址是四字节对齐的。


array2占了3字节的内存空间,给array1分配时本应从array2+3处分配,但array+3不是4的整数倍地址,要对齐内存,就要往后移动一个字节分配了,注意,这个字节的值是随机的。所以array1的开始地址为array2+4,初始化array1[0]~ array1[2]三个值后,在array1[3]~ array1[6]处填入0(数组的初始化为0)。至此可以分析出这两个字符串的内存分布图,从而很容易得出字符串的长度。

 

内存分布图:

|    0013FF74  65 66 67 CC  efg.                <-- array2

|    0013FF78  61 62 63 00  abc.             <-- array1

V   0013FF7C  00 00 00 CC  ....

 

正确的结果就是3,7


 
阅读(2352) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~