如何在C

时间:2015-07-20 22:00:47

标签: c arrays pointers

我正在处理一个项目,我需要知道如何将从文件读取的行存储到动态双指针中。例如,假设我有这个结构:

typedef struct { 
char **data; /*dynamic array of lines */
size_t nused; /*number of lines in the dynamic array */
} lines_t; 

在我的readline函数中:

lines_t readline() { 
    lines_t line_data;
    char line[LINESIZE]; 
    char *data; 
    line_data.data = malloc(sizeof(char *)*sizeof(line));
    line_data.nused = 1;
    while(fgets(line,LINESIZE,fp)) {
       data = line; 
       line_data.data = &data;  
       nalloc++;  
    } 
    printf("%s",*line_data.data); 
    return line_data; 
}  

但是这将始终打印文件中的最后一行,我怎样才能使它能够访问和打印文件中的任何一行?(我想我可能需要索引双指针)

2 个答案:

答案 0 :(得分:3)

试试这个:

lines_t readline() { 

    lines_t line_data;
    char line[LINESIZE]; 
    char *data; 

    // Allocates enough space for the array, but not the text
    line_data.data = malloc(sizeof(char *)* LINESIZE);

    // Zero indexed
    line_data.nused = 0;

    while(fgets(line,LINESIZE,fp)) {

       // Allocates space for each line
       line_data.data[line_data.nused] = malloc(sizeof(char) * (strlen(line) + 1));

       // Copies the string from the buffer
       strcpy(line_data.data[line_data.nused], line);

       // One more line processed
       line_data.nused++;

       // I'm not sure what this is or what it's for
       //nalloc++;
    } 
    printf("%s",*line_data.data); 
    return line_data; 
}  
BTW,回答实际问题。您可以打印所有这样的行:

for (int it=0 ; it < line_data.nused ; ++it) {
    printf("%s", line_data.data[it]);
}

答案 1 :(得分:3)

如果您的系统有,请使用POSIX getline。您可能需要使用strdup复制获得的行,至少如果您在具有相同参数的循环中调用getline

请注意,André Fratelli's answer将行大小限制为LINESIZE,但getline没有此限制(并且可以读取数千个字符的宽行)。当然,如果使用的malloc失败,它将失败。

另见this相关问题。

在像Linux这样的GNU系统上,如果从终端读取,您可能需要使用GNU readline库。它增加了编辑功能(并启用了自动完成功能)。

因此,您的readline名称有点令人困惑。您可以添加注释,告知它不是GNU readline库,或者将名称更改为其他内容,例如read_a_line ....

顺便说一下,你会更好地成长和放大偶尔使用一些newsize = 3*oldsize/2 + 50; geometric progression来分配您的向量。然后你需要保留分配和使用的大小:

typedef struct { 
   char **data; /*dynamic array of nallocated lines */
   size_t nallocated; // allocated size of `data` above
   size_t nused; // count of used lines in the dynamic array
   /// invariant: nused <= nallocated
} lines_t; 

最后,不要忘记测试malloc(&amp; calloc&amp; realloc)和fgetsgetline或{{1}反对失败。在Linux上,在shell中使用readline,调用setrlimit(2)(您希望ulimit),对RLIMIT_AS失败进行压力测试。