C 文本文件到结构体、数组,然后输出

标签 c struct text-files readfile

我正在尝试获取一个简单的书籍信息文本文件并将其存储到一个结构数组中。我刚刚学习 C,与 Java 或 C# 相比,有点困惑。

我知道这与我编写代码的方式有关

我的文本文件是:

Magician:Apprentice
RaymondE.Feist 
Spectra(January1,1994) 
5.02 
0553564943 
512 
1 
Magician:Master 
RaymondE.Feist 
Spectra(January1,1994) 
7.99 
0553564935 
499 
1

然后我有我的代码,我不确定我做错了什么,我知道它与 while(fgets(line... 我知道如何显示所有文本,我只是遇到问题将文本正确存储到结构中。

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

typedef struct book{

char title[100];
char author[100];
char publisher[100];
float price;
char isbn[100];
int pages;
int copies;
} Book;

int main( void )
{

//addInventory( "Magician: Apprentice", "Raymond E. Feist",     5.02, "0553564943", 512, 1 );

//Book myBook = { "Magician: Apprentice", "Raymond E. Feist", "unknown", 5.02, "0553564943", 512, 1 };

//addInventory( myBook );

   char ch, file_name[25];
   FILE *fp;

  printf("Enter the name of file you wish to see\n");
  gets(file_name);

  fp = fopen(file_name,"r"); // read mode

  if( fp == NULL )
  {
  perror("Error while opening the file.\n");
  exit(EXIT_FAILURE);
  }

  //printf("The contents of %s file are :", file_name);

 /*while( ( ch = fgetc(fp) ) != EOF )
  printf("%c",ch);*/


    char line[9001];
    char *item;
    int reccount = 0;
    int k;
    int maxEntries = 100;



    while (fgets(line,9000,fp)) {
            printf("%s",line);


            item = strtok(line,"");
            strcpy(inventory[reccount].title,item);
            printf("1");

            item = strtok(line,"");
            strcpy(inventory[reccount].author,item);
            printf("2");

            item = strtok(line,"");
            strcpy(inventory[reccount].publisher,item);

            item = strtok(line,"");
            inventory[reccount].price = atof(item);

            item = strtok(line,"");
            strcpy(inventory[reccount].isbn,item);

            item = strtok(line,"");
            inventory[reccount].pages = atoi(item);

            item = strtok(line,"");
            inventory[reccount].copies = atoi(item);


            //printf("%s\n",inventory[reccount].publisher);
            reccount++;
            }



    fclose(fp);

printf("My Inventory:\n");  
int i;
for( i = 0; i < count; i++ )
{
    printf( "Title:\t\"%s\"\n", inventory[i].title );
    printf( "Author:\t%s\n", inventory[i].author );
    printf( "Publisher:\t%s\n", inventory[i].publisher );
    printf( "Price:\t$%.02f\n", inventory[i].price );
    printf( "ISBN:\t%s\n", inventory[i].isbn );
    printf( "Pages:\t%d\n", inventory[i].pages );
    printf( "Copies:\t%d\n", inventory[i].copies );
}

    return 0;

}

最佳答案

这不是 fgets 的问题。
首先,fgets 从文件中读取一行文本,strtok 使用分隔符分割字符串。您可能希望像这样设置文件格式:

Magician:Apprentice RaymondE.Feist Spectra(January1,1994) 5.02 0553564943 512 1 
Magician:Master RaymondE.Feist Spectra(January1,1994) 7.99 0553564935 499 1

然后使用""作为分隔符。其次,在第一次使用 strtok 后,传递 NULL 而不是 line。你可以这样做:

item = strtok(line," ");
strcpy(inventory[reccount].title,item);

item = strtok(NULL," ");
strcpy(inventory[reccount].author,item);

item = strtok(NULL," ");
strcpy(inventory[reccount].publisher,item);

item = strtok(NULL," ");
inventory[reccount].price = atof(item);

item = strtok(NULL," ");
strcpy(inventory[reccount].isbn,item);

item = strtok(NULL," ");
inventory[reccount].pages = atoi(item);

item = strtok(NULL," ");
inventory[reccount].copies = atoi(item);

您还可以使用其他分隔符(例如 ;,以便作者姓名中可以有空格),然后您可以像这样设置文件格式:

Magician:Apprentice;Raymond E. Feist;Spectra(January1,1994);5.02;0553564943;512;1 
Magician:Master;Raymond E. Feist;Spectra(January1,1994);7.99;0553564935;499;1

此外,countinventory 均未定义。您可以这样做(在 while(fgets...) 循环之前):

int count = 2;
Book* inventory = malloc(count*sizeof(Book));

或者,如果您希望能够拥有不同大小的文件,只需计算行数,然后关闭并重新打开文件即可:

int count = 0;
while (fgets(line,9000,fp)) count++;
fclose(fp);
fp = fopen(file_name, "r");
Book* inventory = malloc(count*sizeof(Book));

编辑:要保持文件格式不变,您需要为每本书调用 7 次 fgets。不幸的是,fgets 包含换行符,因此您需要使用 strtok

删除它
int count = 0;
while (fgets(line,9000,fp)) count++;
count = count / 7;
fclose(fp);
fp = fopen(file_name, "r");
Book* inventory = malloc(count*sizeof(Book));
int i;

int reccount;
for (reccount = 0; reccount < count; reccount++){


    fgets(line,9000,fp);
    item = strtok(line, "\n");
    strcpy(inventory[reccount].title,item);

    fgets(line,9000,fp);
    item = strtok(line, "\n");
    strcpy(inventory[reccount].author,item);

    fgets(line,9000,fp);
    item = strtok(line, "\n");
    strcpy(inventory[reccount].publisher,item);

    fgets(line,9000,fp);
    inventory[reccount].price = atof(line);

    fgets(line,9000,fp);
    item = strtok(line, "\n");
    strcpy(inventory[reccount].isbn,item);

    fgets(line,9000,fp);
    inventory[reccount].pages = atoi(line);

    fgets(line,9000,fp);
    inventory[reccount].copies = atoi(line);


}

fclose(fp);

关于C 文本文件到结构体、数组,然后输出,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35109070/

相关文章:

unix - 如何更改模板中替换变量的格式

java - 如何从文本文件排序并写入另一个文本文件Java

c - 如何将 CSV 文件读入结构的二维数组,其中每个元素都有一个确定字符(C、G、M)来排序到结构中?

c# - 在 C# 中,结构需要多少内存?

c# - 如何使用结构作为包含字符串的参数进行互操作调用

c++ - 哪个维基解析器?

c++ - 如何将纯文本转换为ODF?

c - 为什么我无法读取服务器文件中的多个字符串?

c - 错误 : `TFD_NONBLOCK' undeclared (first use in this function)

c - 从 TCP 套接字读取错误数据