堆内存还是栈内存?

《剑指Offer》里面有一道题目,“把一字符数组中的空格用字符串“%20”代替“,看了书上的思路,然后我写出来的程序当输入的空格太多时,会出现错误“memory clobbered before allocated block”。其原因是没搞清楚栈内存,堆内存的分配和区别。错误代码如下:

#include <stdio.h>
#include <malloc.h>
#include <string.h>

void replaceSpace(char string[]);

int main()
{
    char string[] = "This is a test!";    //字符数组,在栈内存区分配内存
    replaceSpace(string);

    printf("%s",string);
    free(string);
    return 0;
}

void replaceSpace(char string[])
{
    int index, spaceNum;
    size_t OriginLen, FinalLen;
    int OriginIndex, FinalIndex;

    index = 0;
    spaceNum = 0;
    OriginLen = 0;

    while(string[index] != '\0')
    {
        if(string[index] == ' ')
            spaceNum++;
        OriginLen++;
        index++;
    }

    FinalLen = OriginLen + spaceNum * 2;
    string = realloc(string,FinalLen);        //realloc函数 在堆内存区分配内存

    OriginIndex = OriginLen;
    FinalIndex = FinalLen;

    while(OriginIndex >= 0)
    {
        if(string[OriginIndex] != ' ')
        {
            string[FinalIndex] = string[OriginIndex];
        }
        else
        {
            string[FinalIndex] = '0';
            string[--FinalIndex] = '2';
            string[--FinalIndex] = '%';
        }

        --FinalIndex;
        --OriginIndex;
    }
 }

程序的第9行定义并初始化了一个字符数组string,它的内存分配由系统自动在完成,且是在栈上分配的。

当我在replaceSpace函数中要把string中的空格替换成“%20”的时,需要给它扩展内存,这时我想到了realloc函数。但不幸的是,realloc函数操作的是堆内存,而string的内存是在栈上分配的,所以realloc函数在堆上根本就找不到string所占用内存对应的地址,更别说给它扩展内存空间了。所以这个函数返回一个空值,这也就是报错的原因。

解决方法:

1. 一开始就给string字符数组给足空间,不在replaceSpace函数中重新扩展。

char string[100] = "this is a test!";

2. 使用malloc函数给string分配空间。

int main()
{
     char * string;
     string = (char*)malloc(strlen("test")*sizeof(char));
     strncpy(string,"test",strlen("test"));
     ...
    }

void replaceSpace(char string[])
{
    string = realloc(string,FinalLen);
    ...
    if(string != NULL)
    {
        ...
    }
    else
    {
        printf("alloc memory error!\n");
    }
    ...
}

盗一段代码,(这段代码对于堆和栈的区别说的很清楚啊):


PS. 关于栈,堆内存分配相关文章参考:

     http://bbs.csdn.net/topics/390147637




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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值