从C中的文件读取时无限循环

时间:2014-12-04 08:26:23

标签: c file linked-list

对不起,这有点冗长,但我现在已经被我的代码中的这个讨厌的bug困住了几个小时,而且我真的很绝望。

我正在编写一个基本的Rolodex程序。 Rolodex是一个链接列表,其每个节点存储一个人的名字,姓氏和电话号码(全部为字符串)。 Rolodex的初始内容是从用户指定的文件中读取的,例如:

bash $ ./rolodex bobsRolodex

此rolodex将使用文件" bobsRolodex。"如果用户没有指定文件,则默认为" myRolodex。"每个文件的内容(如果有)将添加到程序开头的链接列表中。然后要求用户输入新联系人,打印列表或退出。当用户退出时,链接列表通过覆盖文件的先前内容来更新文件,始终遵循相同的格式,即在连续的行上:

第一部手机

我遇到的问题是,如果文件中有内容我指定,从文件中读取并尝试将内容插入链接列表会导致无限循环。这是代码;我对给出问题的函数发表了评论:

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

struct Rolodex
{
    char first[40];
    char last[40];
    char phone[40];
    struct Rolodex *next;
};

typedef struct Rolodex r_struct;
r_struct *head = NULL;

void add_card_to_rolodex(r_struct* card)
{
    if(head == NULL)
    {
        card -> next = NULL;
        head = card;
    }
    else
    {
        card -> next = head;
        head = card;
    }
}

void open_and_read_from_file(char* fileName) //PROBLEM IS HERE!!!
{
    FILE* ifp = fopen(fileName, "r");
    if(ifp) //if file exists
    {
        r_struct* card = malloc(sizeof(r_struct));
        card->next = NULL;
        while(fscanf(ifp, "%s %s %s\n", card->first, card->last, card->phone) == 3)
        {
            add_card_to_rolodex(card);
        }
        fclose(ifp);
    }
}

void write_to_file(char* fileName)
{
    FILE* ofp = fopen(fileName, "w");
    r_struct* temp = head;
    while(temp != NULL)
    {
        fprintf(ofp, "%s %s %s\n", temp->first, temp->last, temp->phone);
        temp = temp->next;
    }
    fclose(ofp);
}

void print_rolodex(bool terminal)
{
    int count = 0;
    r_struct *temp = head;
    while(temp != NULL)
    {
        if(terminal)
        {
            printf("%d ", count);
            count++;
        }
        printf("%s %s %s\n", temp->first, temp->last, temp->phone);
        temp = temp->next;
    }
}

char read_command(char* fileName)
{
    char command;
    printf("%s Command: ", fileName);
    scanf("%c", &command);
    getchar();
    return command;
}

void evaluate_command(char command)
{
    if(toupper(command) == 'I') //insert new card
    {
        r_struct *card = malloc(sizeof(r_struct));
        card -> next = NULL;

        printf("Enter card: first-name last-name phone:\n");
        scanf("%s %s %s", card->first, card->last, card->phone);
        getchar();

        add_card_to_rolodex(card);
    }
    else if(toupper(command) == 'P') //print all cards
    {
        bool terminal = true;
        print_rolodex(terminal);
    }
}

void deallocate_memory()
{
    r_struct* temp = head->next;
    if(head != NULL)
    {
        while(temp != NULL)
        {
            free(head);
            head = temp;
            temp = temp->next;
        }
    }
}

int main(int argc, char *argv[])
{
    char *fileName = argv[1];
    char command;

    if(fileName == NULL)
        fileName = "myRolodex";

    open_and_read_from_file(fileName); //PROBLEM IS HERE

    while(command != 'Q')
    {
        command = read_command(fileName);
        evaluate_command(command);
    }

    write_to_file(fileName);
    deallocate_memory();
    return 0;
}

1 个答案:

答案 0 :(得分:4)

基本上,你需要重新安排事情

r_struct* card = malloc(sizeof(r_struct));

适用于您添加到rolodex的每张卡。目前,您只需拨打malloc一次,即可覆盖同一块内存。

或者在add_card_to_rolodex中获取结构的深层副本。

当您要销毁链接列表时,不要忘记清除内存,但要调用free