C语言 动态读取和存储到 char 数组



>我有一个文件,我想从中读取并将数据存储到一个字符数组中,我在每次读取字符后动态分配内存。我想动态地将内存完全分配给所需的大小。这是我所拥有的:

FILE *fp;
char *data;
int c=0;
fp=fopen("home/bob/Downloads/filename", "r");
data=malloc(sizeof(char));
do{
    data[c]=fgetc(fp);
    printf("data : %cn", data[c]);
    c++;
    data=realloc(data, sizeof(char)+c);
} while(data[c]!=EOF);

我遇到分段错误。

问题很可能在这里:

while(data[c]!=EOF)

请记住,您增加了循环内部的c,因此data[c]是您分配的内存的未初始化部分。这意味着只要未初始化的数据不(char) -1,您就会继续逐个字符读取,这可能远远超出文件的实际结尾。

相反,请尝试这样的事情:

char *data = NULL;
size_t c = 0;
for (;;)
{
    const int ch = fgets(fp);
    if (ch == EOF)
        break;  /* Error or end of file */
    char *tmp = realloc(data, c + 1);
    if (tmp == NULL)
        break;  /* Could not allocate memory */
    data = tmp;
    data[c++] = ch;
}

当您的程序尝试评估以下条件时:

(data[c]!=EOF)

c 已递增,因此data[c]尝试访问超出 data 数组范围的元素,从而导致未定义的行为

首先,您必须使用带有 malloc coz malloc 返回 void* 的类型转换*

data=(char*)malloc(sizeof(char));

此外,EOF 不是字符 (EOF=-1)

while 循环中的条件指向内存中尚未初始化的部分。

int ch;
while(1)
{
if( (ch=fgets(fp))==EOF )
    break;
data[c]=ch;
c++;
data=realloc(data, sizeof(char)+c);
}
do{
    data[c]=fgetc(fp);
    printf("data : %cn", data[c]);
    c++;
    data=realloc(data, sizeof(char)+c);
}while(data[c]!=EOF);  // this should be the location of the seg fault

而 (data[c]) 查看数组末尾的后面。

}while(data[c - 1]!=EOF);

或在检查后递增 c

data[c]=fgetc(fp);  --> This gives seg fault 

因为你像这样递增c++

data=malloc(sizeof(char));

data指向sizeof(char)的记忆,当你做c++然后data[c]变成UB。

您已经分配了一个字节的内存。这绝对不足以读取文件。

我建议使用stat()解释如何确定 C 中文件的大小? 获取大小,然后分配size*sizeof(char)

#include <sys/stat.h>
off_t fsize(const char *filename) {
    struct stat st; 
    if (stat(filename, &st) == 0)
        return st.st_size;
    return -1; 
}
{
    FILE *fp;
    char *data;
    int c=0;
    off_t size = fsize("home/bob/Downloads/filename") +1;
    fp=fopen("home/bob/Downloads/filename", "r");
    data=malloc(sizeof(char) * size);
    do{
        data[c]=fgetc(fp);
        printf("data : %cn", data[c]);
        c++;
        data=realloc(data, sizeof(char)+c);
    }while(data[c]!=EOF);
}

相关内容

  • 没有找到相关文章

最新更新