chenyonken 2017-02-05 10:23 采纳率: 0%
浏览 2393
已采纳

二级指针指向内存释放问题

/*要求:将二级指针第一种内存模型和第二种内存模型拷贝到第三种内存模型
int copyptr(char (*myp1)[10],int num1,char **myp2,int num2,char **myp3,int num3);/
问题:释放malloc内存时程序当掉,原因不明
程序当掉的地方在freep01()函数那里,已标记开始当掉之处


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

int sort(char **myp3, int num3)
{
    char **p = myp3;
    char *tmp = NULL;
    int i = 0, j = 0;
    if (myp3 == NULL)
    {
        printf("sort() 函数参数传递出错\n");
        return 1;
    }
    for (i=0; i < num3; i++)
    {
        for (j=i+1; j < num3; j++)//错误,需把内容复制而不是指针交换
        {
            if (strcmp(p[i], p[j]) > 0)
            {
                tmp = p[i];
                p[i] = p[j];
                p[j] = tmp;
            }
        }
    }
    return 0;
}
int copyptr(char (*myp1)[30], int num1, char **myp2, int num2, char ***myp3, int *num3)
{
    int i = 0, j = 0, k = 0;
    char **p3 = NULL;
    p3 = (char **)malloc(sizeof(char *) * (num1 + num2));
    if (p3 == NULL)
    {
        printf("copyptr() 分配p3二级指针内存失败\n");
        return 1;//注意此时还没释放内存
    }
    if (myp1 == NULL || myp2 == NULL || myp3 == NULL || num3 == NULL)
    {
        printf("参数传递出错\n");
        return 2;
    }
    char(*p1)[30] = myp1;
    char **p2 = myp2;
    *num3 = num1 + num2;
    for ( i = 0; i < num1; i++)//拷贝第一种内存
    {
        k = strlen(p1[i])+1;
        p3[i] = (char *)malloc(sizeof(char)*k);
        strcpy(p3[i], p1[i]);
        p3[i][k] = '\0';
    }
    for (j = 0; j < num2; j++,i++)//拷贝第二种内存
    {
        k = strlen(p2[j]) + 1;
        p3[i] = (char *)malloc(sizeof(char)*k);
        strcpy(p3[i], p2[j]);
        p3[i][k] = '\0';
    }
    int ret = sort(p3, *num3);
    if (ret != 0)
    {
        printf("sort() err\n");
        return 3;
    }
    *myp3 = p3;
    return 0;
}

int freep01(char **myp, int num)
{
    char **p = myp;
    if (myp == NULL)
    {
        return 1;
    }
    for (int i = 0; i < num; i++)
    {
        free(p[i]);//运行到这里程序当掉
        p[i] = NULL;
    }
    free(p);
    p = NULL;
    return 0;
}
int freep02(char ***myp, int num)
{
    char **p = *myp;
    if (myp == NULL)
    {
        return 1;
    }
    for (int i = 0; i < num; i++)
    {
        free(p[i]);
        p[i] = NULL;
    }
    free(p);
    p = NULL;
    return 0;
}
void main()
{
    char p1[][30] = { "aaaaaa","bbbbb","ccccccc" };
    char *p2[] = { "1111","222222","33333333"};
    char **p3 = NULL;
    int len1 = sizeof(p1) / sizeof(p1[0]);
    int len2 = sizeof(p2) / sizeof(p2[1]);
    int len3 = 0;
    int ret = copyptr(p1, len1, p2, len2, &p3, &len3);
    if (ret != 0)
    {
        printf("copyptr() err\n");
        return;
    }
    for (int i = 0; i < len3; i++)
    {
        printf("%s\n", p3[i]);
    }
    printf("总共%d个字符串\n", len3);

    ret = freep01(p3, len3);
    if (ret != 0)
    {
        printf("freep01() err\n");
        return;
    }

}

图片说明

  • 写回答

3条回答 默认 最新

  • miaochunlei 2017-02-10 01:57
    关注

    int copyptr(char (*myp1)[30], int num1, char **myp2, int num2, char ***myp3, int num3)
    {
    int i = 0, j = 0, k = 0;
    char **p3 = NULL;
    p3 = (char *
    )malloc(sizeof(char *) * (num1 + num2));
    if (p3 == NULL)
    {
    printf("copyptr() 分配p3二级指针内存失败\n");
    return 1;//注意此时还没释放内存
    }
    if (myp1 == NULL || myp2 == NULL || myp3 == NULL || num3 == NULL)
    {
    printf("参数传递出错\n");
    return 2;
    }
    char(*p1)[30] = myp1;
    char **p2 = myp2;
    *num3 = num1 + num2;
    for ( i = 0; i < num1; i++)//拷贝第一种内存
    {
    k = strlen(p1[i])+1;
    p3[i] = (char *)malloc(sizeof(char)*k);
    strcpy(p3[i], p1[i]);
    p3[i][k-1] = '\0';//【注释】//将k改为k-1,长度为k,最后一个元素为k-1,前面释放未申请内存,故报错;
    }
    for (j = 0; j < num2; j++,i++)//拷贝第二种内存
    {
    k = strlen(p2[j]) + 1;
    p3[i] = (char *)malloc(sizeof(char)*k);
    strcpy(p3[i], p2[j]);
    p3[i][k-1] = '\0';//【注释】//将k改为k-1,长度为k,最后一个元素为k-1,前面释放未申请内存,故报错;
    }
    int ret = sort(p3, *num3);
    if (ret != 0)
    {
    printf("sort() err\n");
    return 3;
    }
    *myp3 = p3;
    return 0;
    }

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(2条)

报告相同问题?

悬赏问题

  • ¥15 labview程序设计
  • ¥15 为什么在配置Linux系统的时候执行脚本总是出现E: Failed to fetch http:L/cn.archive.ubuntu.com
  • ¥15 Cloudreve保存用户组存储空间大小时报错
  • ¥15 伪标签为什么不能作为弱监督语义分割的结果?
  • ¥15 编一个判断一个区间范围内的数字的个位数的立方和是否等于其本身的程序在输入第1组数据后卡住了(语言-c语言)
  • ¥15 游戏盾如何溯源服务器真实ip?
  • ¥15 Mac版Fiddler Everywhere4.0.1提示强制更新
  • ¥15 android 集成sentry上报时报错。
  • ¥50 win10链接MySQL
  • ¥15 抖音看过的视频,缓存在哪个文件