从文件

时间:2017-04-05 21:04:13

标签: c pointers malloc

我有一个文件,每行字符串都是这种格式

key1 = value1
key2 = value2
....

我需要在第三列中提取字符串。我到目前为止编写的代码是

    fp = fopen(file, "r");
    assert(fp && "checkpoint file not found  \n");

    char **data = (char **) malloc(sizeof (char*) * lines ); // lines=100
    size_t i = 0;

    while ((read = getline(&line, &len, fp)) != -1){
        size_t l = strlen(line);

        char value[256];
        sscanf( line, "%s %s %s", field, tmp, value); // field stores 'key1', tmp stores '+', value stores 'value1'

        data[i] = value;
        i++;
        printf("%s \n", value);
        // printf("%s %s\n", value, data[i]); -- when this line is uncommented, it leads to a seg-fault.
    }
    fclose(fp);


      for (int i=0; i < lines; ++i)
        free(data[i]);
      free(data);

我收到错误“对象的malloc错误..,未释放指针被释放”。

3 个答案:

答案 0 :(得分:1)

我认为问题出在

之前
  printf("%s %s\n", value, data[i]);

这一行,您正在i++更改i的值。然后data[i]指向未初始化的内存。将其作为参数传递给%s会导致undefined behavior

[编辑:

然后,你正在做

 free(data[i]);

然而,data[i]不是内存分配器函数返回的指针。这是UB的另一个原因。

那就是说,

答案 1 :(得分:0)

观察到的错误的直接原因是:

char value[256];
//....
data[i] = value;

以及稍后(在后续循环中):

free(data[i]);

您正在释放静态分配的数组。

你想:

char *value=malloc(sizeof(char)*256);

我知道sizeof(char)==1的定义。这只是一种很好的做法。

答案 2 :(得分:0)

声明char value[256]在功能堆栈上保留一些空间。对于不同的data[i],您的i会一直指向堆叠中的同一个位置。请注意,value太小时,堆栈上可能存在溢出问题,除非其大小有固定限制。此堆栈区域未分配,因此无法释放,因此错误。

结果是data[i]在第一次弃权后被所有其他行覆盖。每次都会获得一个指向同一区域的(不可释放的)指针。您需要将该值复制到tyour自己的指针:你还需要做的是在最后释放变量line(因为它获得了一个malloc-ed指针值并被重新分配以使其适合该行。),并为每一行做{{{ 1}}创建指向 copy malloc的指针并将value设置为该新指针。所以你的代码中存在各种各样的问题。