在本教程中,您将通过示例掌握有关 C 语言文件和文件操作的所有知识。您将了解什么是文件、如何打开和关闭文件,以及通过 C 编程读写文件的一些基本方法。
文件是具有特定名称的字节集合。确切地说,文件是系统存储上的一个命名位置,用于存储相关数据以供将来使用。数据可以是任何东西,如简单的文本文件、视频或音频文件,或任何复杂的可执行程序。我们使用文件系统在硬盘等非易失性内存中实现持久存储。
当我们编译和运行一个程序时,我们肯定会得到一个输出。一旦我们退出程序,所有的输入和输出都会从内存中被清除。I/O 函数帮助我们将这些数据以文件的形式存储在硬盘或可移动磁盘上,从而确保数据的永久存储。另一个原因是,在处理大量数据时,文件很容易操作,因为将大量数据输入程序根本不被认为是一种好的做法。存储在文件中的数据可以使用文件命令进行访问。此外,文件在计算机之间传输也很方便。
文件分为两种类型

下面列出了在处理文件时需要执行的 4 种基本操作。它们按处理顺序列出。

由于文件存储在磁盘上,我们需要通过声明一个文件类型的指针在文件和程序之间建立链接,如下所示。
FILE *fptr;
然后我们可以先打开一个文件以便读取或写入它。fopen() 函数通常用于完成这项工作。它告诉操作系统打开文件名以及打开它的原因。如果操作系统成功做到这一点,它会将文件第一个字节的地址作为指向文件结构的指针发送回来。该函数的原型是
FILE *fopen (const char *filename, const char *mode);
其中
假设我们想以读取目的打开一个名为“Data.dat”的文件。在这种情况下,参数将是
FILE *fptr;
fptr= fopen("DATA.dat", "r");
这里的“r”表示文件将是只读的。显然,参数的第二个参数决定了文件的属性。
这是显示不同文件打开模式的表格。
| 模式 | 含义 | 描述 |
|---|---|---|
| r | 读取 | 打开一个文本文件进行读取。如果文件不存在,fopen() 返回 Null。 |
| w | 写入 | 以只写模式打开文本文件以进行覆盖。如果文件不存在,则创建一个文件。 |
| a | 追加 | 在文件末尾追加内容而不截断现有内容。如果文件不存在,则创建一个文件。 |
| r+ | 读写 | 打开文件进行读写 |
| w+ | 读写 | 以写读模式打开文件 |
| a+ | 追加读写 | 以追加模式打开文件进行读写。 |
| rb | 二进制读取 | 打开一个二进制文件进行读取 |
| wb | 二进制写入 | 打开一个二进制文件进行写入。 |
| ab | 二进制追加 | 打开一个二进制文件以在文件末尾追加 |
| rb+ | 二进制读写 | 打开一个二进制文件进行读写 |
| wb+ | 二进制读写 | 打开一个二进制文件进行写读 |
| ab+ | 二进制追加读写 | 以读写模式打开一个二进制文件进行追加 |
在读取或写入后,我们必须关闭它,fclose() 函数负责这项工作。该函数的原型在 <stdio.h> 头文件中声明。
fclose(fp);
该函数使用 fp,一个指向 FILE 结构的指针,与 fopen 函数完全相似。当我们将数据写入文件时,它首先存储在缓冲区中。当缓冲区变满或编译器遇到 fclose() 函数时,数据才真正写入磁盘。
有几个函数可用于从文件中读取数据和向文件中写入数据。下面将这些函数列表化以便于理解。
| 序号 | 函数 | 描述 |
|---|---|---|
| 1 | fprintf() | 将数据写入文件 |
| 2 | fscanf() | 从文件中读取数据 |
| 3 | fputc() | 将一个字符写入文件 |
| 4 | fgetc() | 从文件中读取一个字符 |
| 5 | fseek() | 将文件指针设置到特定位置 |
| 6 | fputs() | 将一个字符串写入文件 |
| 7 | fgets() | 从文件中读取一个字符串 |
| 8 | ftell() | 返回当前位置 |
| 9 | rewind() | 将文件指针设置到开头 |
| 10 | fread() | 从二进制文件读取数据 |
| 11 | fwrite() | 向二进制文件写入数据 |
要向文本文件写入内容,最简单的是 putc。其原型如下:
putc (int ch, FILE *stream);
这里是一个例子,说明了该函数的应用。
#include <stdio.h>
main()
{
FILE *fp;
char ch;
fp= fopen ("FILE.txt", "w");
while ((ch=getche()) != '\r')
putc (ch, fp);
}
在这个程序中,getche 会接收单个字符输入并将其存储在变量 ch 中。putc 将使用文件指针 fp 将该字符写入目标文件“FILE.txt”。

fputs 是另一个函数,能够一次性将一个字符串写入文件。其语法是
fputs (const char *str, FILE *stream);
fgetc 函数是读取文件内数据的最简单工具。该函数的原型是
fgetc(FILE *stream);
我们可以使用 'while 循环' 来读取多个字符。
while ((ch= fgetc (fp)) !=EOF)
printf ("%c", ch);
就像 'fputs' 一样,有一个名为 'fgets' 的函数。如果输入流引用有 'n' 个字符,那么它将能够读取 (n-1) 个字符。
假设我们有一个名为 myfile.txt 的文件,如下所示,其中包含一些数据。

让我们编写一个简单的 C 程序,使用 fgetc 来读取该文件。
#include<stdio.h>
void main()
{
FILE *fp;
char c;
fp=fopen("myfile.txt","r");
while((c=fgetc(fp))!=EOF){
printf("%c",c);
}
fclose(fp);
}
该程序输出文件 myfile.txt 中包含的数据,并且在控制台上打印的输出是
This is how we read data in a file using C programming.
到目前为止,我们已经讨论了文本文件。但是我们也可以通过 C 编程来读取、写入或编辑二进制文件。在这种情况下,第二个参数是 'rb' 而不是 'r'。同样,'w' 被 'wb' 替换。
fp= fopen ("binary.bin", "rb");
在文本文件中,'\n'被视为单个字符,而在二进制文件中它被视为两个连续的字符。此外,我们不能在二进制文件的末尾添加任何“文件结束”字符。
'fread' 和 'fwrite' 是基本函数,主要用于读写这类文件。它们的原型是
size_t fwrite (void *buf, int size, int, count, FILE *fp);
and
size_t fread (void *buf, int size, int, count, FILE *fp);
检查下面的程序,它写入结构体
#include<stdio.h>
#include<stdlib.h>
struct Book
{
char Title[20];
int price;
};
int main()
{
struct Book B;
FILE *fp;
fp=fopen("Book.txt","wb");
if(fp==NULL)
{
printf("Error: Cannot open file");
exit(1);
}
printf("\n Enter the title of the book:");
gets(B.Title);
printf("\n Enter the price of the book:");
fflush(stdin);
scanf("%d",&B.price);
fwrite(&B,sizeof(struct Book),1,fp);
printf("Data is stored in th file successfully in binary format");
fclose(fp);
return 0;
}
输出
Enter the title of the book:Alchemist Enter the price of the book:1500 Data is stored in the file successfully in binary format
在上面的程序中,我们创建了一个名为 Book 的结构体,其成员为 Title 和 Price。在 main 函数中,我们声明了一个文件指针 fp,并打开了 Book.txt 文件以写入书的标题和价格。但我们需要以二进制格式存储数据,所以我们使用了 fwrite() 函数。之后,您可以转到文件位置,检查文件内部存储了哪些详细信息。由于详细信息是以二进制格式存储的,您只能读取少量数据。
为了以二进制格式读取数据,您可以使用 fread() 函数,如下面的程序所示。
#include<stdio.h>
#include<stdlib.h>
struct Book
{
char Title[20];
int price;
};
int main()
{
struct Book B;
FILE *fp;
fp=fopen("Book.txt","rb");
if(fp==NULL)
{
printf("Error: Cannot open file");
exit(1);
}
fread(&B,sizeof(struct Book),1,fp);
printf("\nTITLE OF BOOK : %s",B.Title);
printf("\nPRICE OF BOOK : %d",B.price);
fclose(fp);
}
输出
TITLE OF BOOK : Alchemist PRICE OF BOOK : 1500