c - 如何存储和读取文件中的数据

标签 c file

我是 Linux 中的 C 新手。我正在尝试将数据存储到文件中并将其读回。这是正确的方法吗?当我尝试编译这个时,我收到错误。任何人都可以帮助我吗?提前致谢。

 #include<stdio.h>
       typedef struct
    {
      int select;
      char lastname[25];
      char firstname[25];
      char address[25];
      char phonenumber[25];
    } addressbook;

    addressbook a[5];
     FILE *fp;
    int main()
    {
      int i;

     for( i=0; i<5 ; i++)
    {
     printf("enter details\n");
       printf("enter lastname:\n");
       scanf("%s", a[i].lastname);
       printf("enter firstname:\n");
       scanf("%s", a[i].firstname);
       printf("enter address:\n");
       scanf("%s", a[i].address);
       printf("enter phone number:\n");
       scanf("%s", a[i].phonenumber);
      fp = fopen("addressbook.dat","a+");
      fwrite(&a, sizeof(a), 1, fp);
      fclose(fp);
    }

    for(i=0; i<5; i++)
    {
      fopen("addressbook.dat", "r");
      fread(&a, sizeof(a), 1, fp );
      printf("lastname:%s\n", a[i].lastname);
      printf("firstname:%s\n", a[i].firstname);
      printf("address:%s\n", a[i].address);
      printf("phonenumber:%s\n", a[i].phonenumber);
      fclose(fp);
    }
    return 0;
    }

我没有得到任何输出。它是空白的。

最佳答案

查看这段代码,让我向您解释一下您的代码中出了什么问题。

    #include<stdio.h>

    typedef struct
    {
          int select;
          char lastname[25];
          char firstname[25];
          char address[25];
          char phonenumber[25];
    } addressbook;

    #define ARRAYLEN 2

    addressbook a[ARRAYLEN];
    FILE *fp;

    int main()
    {
         int i;

         fp = fopen("addressbook.dat","a+");

         for( i=0; i<ARRAYLEN ; i++)
         {
           printf("enter details\n");
           printf("enter lastname:\n");
           scanf("%s", a[i].lastname);
           printf("enter firstname:\n");
           scanf("%s", a[i].firstname);
           printf("enter address:\n");
           scanf("%s", a[i].address);
           printf("enter phone number:\n");
           scanf("%s", a[i].phonenumber);
           fwrite(&a[i], sizeof(a), 1, fp); /* notice, array indexed */
        }
        fclose(fp);

        fopen("addressbook.dat", "r");
        for(i=0; i<ARRAYLEN; i++)
        {
          fread(&a[i], sizeof(a), 1, fp );
          printf("lastname:%s\n", a[i].lastname);
          printf("firstname:%s\n", a[i].firstname);
          printf("address:%s\n", a[i].address);
          printf("phonenumber:%s\n", a[i].phonenumber);
        }
        fclose(fp);

        return 0;
    }

实际上,您的代码(除了您已经完成的编辑之外)并没有那么不正确,但它有一些小而关键的缺陷。

  1. 唯一真正的变化是:-

    fwrite(&a[i],...
    

    并且,

    fread(&a[i],...
    

    即传递要写入的特定数组元素的地址,而不是整个数组。另外,即使您传递了整个数组的地址,编号也是如此。您要求库写入的字节/字符数只是 sizeof(结构),因此本质上其余部分被截断。如果没有这个,你写入文件的内容就像......

    A          <-- file contents after, first iteration
    AAB        <-- file contents after, second iteration
    AABABC     <-- file contents after, third iteration
    AABABCABCD <-- file contents after, fourth iteration
    ....
    

    我想你会从中找出问题所在。而且你的addressbook.dat的内容是文本,所以一个简单的“cat addressbook.dat”(在Linux上)会告诉你出了什么问题:-)

  2. 您在每次迭代中打开和关闭文件。现在这不是一个错误,而只是一个次优的事情,而且很可能是您不想做的事情。文件操作的成本很高,打开/关闭这些操作会花费相当多的 CPU 周期。您最好为所有写入打开一次文件,为读取打开一次文件。 (当然,一次可以删除在写 block 之后完成的 fclose() 和在读 block 之前完成的 fopen() ,只需将文件指针指向文件的开头 - 留给您练习)。

  3. 在测试时,没有人愿意输入这么多数据。因此,我添加了一个#define(并且使用较新的编译器,您也可以将其替换为 const 定义),它定义了一个保存地址簿数组大小的宏。为了进行测试,我将其保留为“2”。对于生产,您只需将该值更改为“1000”,它仍然可以工作。再说一次,这不是一个错误,只是一种更好的风格,如果你愿意的话。

  4. 哦,顺便说一句,请确保缩进正确。你来自Python世界吗?或者它可能是 SO 发布代码块所需的缩进的产物。

HTH

关于c - 如何存储和读取文件中的数据,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7278491/

相关文章:

C 头文件格式

android - 无法使用 OkHttp3 在文件管理器中选择文件

c - 在编译时重写或中断 C 单元测试的函数链接

c - 从 const char 指针到 char 指针的赋值不给出警告

c - 打印出文件中有多少个字母表中的每个字符。 - C

javascript - 在 Firefox 中设置 FileInput 的 FileList

php - 通过 exec() 将 DirectoryIterator 的实例传递给另一个脚本未按预期工作

检查 C 中对可变长度数组的支持

c++ - 有标准的文件保存和交换模式吗?

c - fgetc,getc 导致程序在读取文本文件时崩溃