在C语言中将格式化文件读入字符数组

3

我有一个非常简单的问题。我需要在C中将文件内容读入到char数组中。该文件将始终格式化为两列字母,例如:

A B
B C
E X
C D

每个字母代表图中的一个顶点,稍后我将处理它。我学过使用C++和Java编程,但对于C并不是特别熟悉。
导致问题的原因是文件有多行。我需要每个字母占据数组中的一个位置,所以在这种情况下,它应该是: array[0] = 'A',array[1] = 'B',array[2] = 'B',array[3] = 'C'等等。
最终,我需要数组不包含重复项,但我可以稍后处理。本学期早些时候,我写了一个从文件中读取单行整数的程序,它很好用,所以我复制了大部分代码,但在这种情况下不起作用。这是我目前的代码:
#include <stdio.h>
#include <stdlib.h>

int main (int argc, char *argv[])
{
   int i;
   int count = 0;
   char * vertexArray;
   char ch = '\0';

// open file
   FILE *file = fopen( argv[1], "r" );

// count number of lines in file
   while  ((ch=fgetc(file)) != EOF)
        if(ch == '\n') count++;

// numbers of vertices is twice the number of lines
   int size = count*2;

// declare vertex array
    vertexArray = (char*) calloc(size, sizeof(char));

// read in the file to the array
   for(i=0; i<size; i++)
        fscanf(file, "%c", &vertexArray[i]);

// print the array
   for(i=0; i<size; i++)
        printf("%c\n", vertexArray[i]);

   fclose( file );
}

我知道我需要测试文件是否正确打开和读取等,但我会稍后添加。现在只是尝试读取数组。在这种情况下,我的输出是8个空行。任何帮助都将非常感激!

4个回答

1
当您循环文件以计算行数时,文件指针已经停留在EOF,因此您不会将任何内容读入数组中。最好情况下,它将与您的最后一个字符相同,但它可能会显示分段错误。
您想要做的是:
rewind(file);

在你之前

//read file into the array

如果您使用 fgetc 函数,则将从文件的开头开始读取。此外,我不确定 fgetc 如何处理行尾,因为通常会有一个尾随的 '\0' 存在。另一种方法是使用 fscanf 函数,如下所示:

i = 0;
while (!feof(file)){
   fscanf(file, "%c %c", &vertexArray[i], &vertexArray[i+1]);
   i++;
}

feof(FILE *)函数检查是否设置了EOF标志,并在遇到EOF时停止。

更新:我认为如果将ch定义为int ch,应该可以工作。请看this线程。

这是对我有效的代码:

int main (int argc, char *argv[])
{
    int i;
    int count = 0;
    char * vertexArray;
    int ch, size;

    FILE *file;
    file = fopen(argv[1], "r");

    while ((ch = fgetc(file) != EOF))
       count++;

    size = count*2;
    vertexArray = (char*) calloc(size, sizeof(char));
    rewind(file);

    for(i=0; i<size; i++)
       fscanf(file, "%c ", &vertexArray[i]);

    for(i=0; i<size; i++)
       fprintf(stderr, "%c\n", vertexArray[i]);

    fclose(file);

}

新编辑 注意在fscanf(file, "%c ", &vertexArray[i]);之后的空格。这告诉C,您想要在读取字符后跳过所有的空白。如果没有空格,它也会将空格读取为一个字符。这应该可以解决问题。


你的建议看起来应该是可行的,但是当我尝试时却出现了分段错误。这似乎与 rewind(file) 有关。我也尝试了 fseek(file, 0, SEEK_SET),但是还是一样。我不知道为什么会出现这种情况。 - DaBurto
抱歉,我实际上还没有尝试过这个来告诉你是否有效,我应该提到一下。我会真正去尝试一下并且告诉你结果。 - Kitchi
由于某种原因,它似乎在读取额外的行?使用此代码,我的计数=20,使大小=40,其中它们应分别为4和8(或9?包括NULL终止符吗?不确定)。 - DaBurto
是的!那很完美地解决了问题,非常感谢您的卓越帮助!我已经快要崩溃了,哈哈。 - DaBurto

0

你需要添加 fseek(file, 0, SEEK_SET);

你的代码应该是这样的:

//Some stuff

// declare vertex array
vertexArray = (char*) calloc(size, sizeof(char));

fseek(file, 0, SEEK_SET);
// read in the file to the array
   for(i=0; i<size; i++)
        fscanf(file, "%c", &vertexArray[i]);

//Some stuff

0

fgetc函数会推进文件位置指针。您需要使用当前代码将其回溯到0,或者在不关心行数的情况下读取行。


0

当你开始读取数据时,你已经用行数计算完文件了。你必须倒回或重新打开文件。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接