一个C语言指针问题

今天重新拿起C语言的书学习学习,遇到了一个诡异的问题,开始不可理解,现在记录下整个分析过程。
首先上代码:
#include <stdio.h>

void strcopy(char *s, char *t)
{
while ((*s++ = *t++) != '\0')
;
}

int main()
{
int i = 3;
char a[] = "abcdefg";
char *p;
strcopy(p, a);
printf("%d\n",i);
}

我估计大多数人看到这个程序都会认为会打印出3,但是结果出乎意料:

[img]http://dl.iteye.com/upload/attachment/504789/6476614d-9bb5-3ae5-8669-4c577743327f.bmp[/img]
于是我分别做了两次修改,都使程序正常了。
第一次,我把strcopy函数注释掉了
#include <stdio.h>

void strcopy(char *s, char *t)
{
while ((*s++ = *t++) != '\0')
;
}

int main()
{
int i = 3;
char a[] = "abcdefg";
char *p;
//strcopy(p, a);
printf("%d\n",i);
}

打印结果是3.
第二次,我把int i = 3;移动p指针下面定义:
#include <stdio.h>

void strcopy(char *s, char *t)
{
while ((*s++ = *t++) != '\0')
;
}

int main()
{
char a[] = "abcdefg";
char *p;
int i = 3;
strcopy(p, a);
printf("%d\n",i);
}

也得到了正确的结果。
于是我用C free对原来的程序进行调试。
[img]http://dl.iteye.com/upload/attachment/504809/b84d982c-b290-3a33-a1ed-7a722154392d.bmp[/img]
找到变量i的内存地址,可知其存放的是00000003,也就是数字3。
接着我执行strcopy方法后,就出状况了:

[img]http://dl.iteye.com/upload/attachment/504811/a4a5014c-5594-39ae-852c-6a19654ae7f5.bmp[/img]
结果表明字符串被拷贝到了变量i的内存地址处。我对i处内存的内容进行十六进制转十进制,64636261转十进制后正好是1684234849.也就是这个诡异的输出结果。
综合以上的分析,所得结果如下:
#include <stdio.h>

void strcopy(char *s, char *t)
{
while ((*s++ = *t++) != '\0')
;
}

int main()
{
int i = 3; //定义int型变量i,分配内存空间,并赋值
char a[] = "abcdefg";
char *p; //定义指针p,并为初始化指针的位置,在此程序中p默认指向了i的地址
strcopy(p, a);
printf("%d\n",i);
}

现在真相大白了,不过任然让我疑惑的在指针p被定义的时候,p的默认指向地址是否有规律可循呢?任旧是个疑问,还请看到这篇文章的各位童鞋指点一二。
不过这个程序本来就是写的有问题,C语言的内存分配果然很容易出错(⊙o⊙)…
我想正确的程序应该是这样的...
#include <stdio.h>

void strcopy(char *s, char *t)
{
while ((*s++ = *t++) != '\0')
;
}

int main()
{
int i = 3;
char a[] = "abcdefg";
char *p = (char *)malloc(sizeof(a)); //给指针分配新的内存空间
strcopy(p, a);
printf("%d\n",i);
}

另外,搜索了下,函数malloc()和函数calloc() 的主要区别是前者不能初始化所分配的内存空间,而后者能。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值