2

我需要编写一个程序来读取文件,然后将单词保存到链表中以供进一步使用。我决定使用 fgetc 逐个字符地读取文本,然后在每次检测到换行符 ( '\n') 或空格 ( ' ') 时将所有内容保存到列表中,表示一个单词。对不起,我是文件指针的新手,这是我到目前为止所得到的:

struct list { //global
char string[30];
struct list *next;
};


int main(void) {

    FILE *filePtr;
    char file[] = "text.txt";
    char tempStr[30];
    list *curr, *header;
    char c;
    int i = 0;
    curr = NULL;
    header = NULL;

    if((filePtr = fopen(file, "r")) == NULL) {
        printf("\nError opening file!");
        getchar();
        exit(101);
    }
    printf("\nFile is opened for reading.\n");

    while(!EOF) {
        while((c = fgetc(filePtr) != ' ') && (c = fgetc(filePtr) != '\n')) {
            curr = (list*)malloc(sizeof(list));
            //c = fgetc(filePtr);
            tempStr[i] = fgetc(filePtr);
            i++;
            }

        tempStr[i] = '\0';

        strcpy(curr->string, tempStr);
        curr->next = header;
        header = curr;

        i = 0;
    }

    while(curr!=NULL) {
        printf("%s - ", curr->string); //This will not print.
        curr = curr->next;
    }

    if(fclose(filePtr) ==  EOF) {
        printf("\nError closing file!");
        getchar();
        exit(102);
    }
    printf("\nFile is closed.\n");

    getchar();
    getchar();

}

如果是文本文件:

have a nice day

期望的输出:

have - a - nice - day

但是,除了打开和关闭的文件之外,我无法打印出任何内容。

谢谢。

4

5 回答 5

1

EOF的值为-1,是定义在 中的系统宏stdio.h。文件读取 API( fgetc, fread, fscanf) 将在到达文件末尾时返回 -1。因此,在您的程序中,while(!EOF)这将始终为假,因为始终为 0。NOT将用 2 的补码表示,因此该变量的所有位都将为 1。(如果大小为 2,将存储为变量)。-1-1int-10xFFFFint

使用下面的示例代码。

while(EOF != (c = fgetc(filePtr))) 
{

    if ((c == ' ') || (c == '\n'))
    {
        if (i == 0)
        {
            continue;
        }

        tempStr[i] = '\0';
        i = 0;

        //here do your linklist node creation and insertion operation

           continue;
    }

    tempStr[i] = c;
    i++;
}
于 2012-06-23T10:03:34.293 回答
0
  • 这总是错误的:

    while(!EOF)
    
  • 查看您的内存分配代码。

    curr = (list*)malloc(sizeof(list))
    
  • 文件的末尾可能没有换行符。

    while((c = fgetc(filePtr) != ' ') && (c = fgetc(filePtr) != '\n'))
    
于 2012-06-23T09:39:00.710 回答
0
while(!EOF) {

这是一个始终为假的恒定条件,因此您永远不会阅读任何内容。

你的代码还有其他问题,比如做

curr = (list*)malloc(sizeof(list));

在一个循环中,但在循环外使用 curr 。

于 2012-06-23T09:39:39.243 回答
0

你应该用你用来读取文件的任何函数替换 while 条件 - 你确定 fgets 没有比这更有效吗?

IE 将字符串读取到比您预期的要大得多的缓冲区中,然后将其复制到适当大小的缓冲区中并将其附加到节点。

于 2012-06-23T09:46:55.267 回答
0

剧透:

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

struct list {
    struct list *next;
    char string[30];
    };

int main(void) {

    FILE *fp;
    char file[] = "llist4.c";
     /* in C you CANNOT omit the "struct keyword" from a declaration or definition. */
    struct list *head=NULL, **pp= &head;
    int ch; /* getc() returns an int */
    size_t len ;
    char buff[30];

    fp = fopen(file, "r");
    if (!fp) {
        fprintf(stderr, "\nError opening file!");
        exit(EXIT_FAILURE);
    }
    printf("\nFile has been opened for reading.\n");

    for (len=0; len < sizeof buff;   ) {
        ch = fgetc(fp);
        if (ch == EOF && !len) break;
        if (ch == ' ' || ch ==  '\n' || ch == EOF) {
            if (!len) continue;
            buff[len] = '\0';
            *pp = malloc(sizeof **pp);
            if (!*pp) break;
            strcpy((*pp)->string, buff);
            (*pp)->next = NULL;
            pp = &(*pp)->next ;
            len=0; continue;
            }

        buff[len++] = ch;
    }

    if (len) {
        fprintf(stderr, "\nWord was too large, or out of memory\n");
        }

    for( ;head; head= head->next) {
        printf("%s - ", head->string);
    }

    if (fclose(fp) ==  EOF) {
        fprintf(stderr, "\nError closing file!\n");
        exit(EXIT_FAILURE);
    }
    printf("\nFile has been closed.\n");
exit(EXIT_SUCCESS);
}
于 2012-06-23T14:10:38.867 回答