c语言中返回指向临时变量的指针的探讨

今天在CSDN的一个Blog上看到了一篇讲C/C++中常见内存错误的文章,里面讲到了 返回指向临时变量的指针会导致不可预料的后果,原文如下:
10.返回指向临时变量的指针
大家都知道,栈里面的变量都是临时的。当前函数执行完成时,相关的临时变量和参数都被清除了。不能把指向这些临时变量的指针返回给调用者,这样的指针指向的数据是随机的,会给程序造成不可预料的后果。
下面是个错误的例子:


下面这个例子没有问题,大家知道为什么吗?


我在VC++6.0上一试,果然前者有问题,后者没有问题。于是就在想为什么会不一样,看了反汇编代码有请教了一位朋友,才明白了其中的原因,相关语句的反汇编代码如下:
7:        char *str = {"abcd"};
0040D798   mov         dword ptr [ebp-4],offset string "abcd" (00422fa4)
11:       return str;
0040D79F   mov         eax,dword ptr [ebp-4]

7:        char str[] = {"abcd"};
0040D798   mov         eax,[string "abcd" (00422fa4)]
0040D79D   mov         dword ptr [ebp-8],eax
_max_test:
0040D7A0   mov         cl,byte ptr [string "abcd"+4 (00422fa8)]
0040D7A6   mov         byte ptr [ebp-4],cl
11:       return str;
0040D7A9   lea         eax,[ebp-8]


"abcd"是编译时放在代码段中的一个无名常量,当程序载入内存的时候是放在另一段内存中的,而非堆栈所在的内存中。从汇编代码中也可以看出,使用char *str这种方式时,程序是把"abcd"所在的内存地址先放到了堆栈中,然后再放入eax作为返回值的,也就是说eax中的地址指向的是"abcd"所在的内存。而用char str[]这种方式是,是先把原来的"abcd"复制到堆栈中的,然后再把存储"abcd"的堆栈的地址放入eax的,也就是说eax中的地址指向的是堆栈中"abcd",而不是原来的那个"abcd",由于函数使用的堆栈中的内存在函数退出后就会被释放,所以作为返回值的指向堆栈的指针就有可能会造成内存错误。后来我又实验了动态分配内存,由于动态分配的内存是在堆上的,所以不会造成上述的内存错误。

  • 1
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值