文件的读取与操作

文件类型:

从文件功能的角度来分类:

1.程序⽂件
程序⽂件包括源程序⽂件(后缀为.c),⽬标⽂件(windows环境后缀为.obj),可执⾏程序(windows 环境后缀为.exe)。
2. 数据⽂件
⽂件的内容不⼀定是程序,⽽是程序运⾏时读写的数据,⽐如程序运⾏需要从中读取数据的⽂件,或 者输出内容的⽂件。

按数据的组织形式分:

1.二进制文件

数据在内存中以⼆进制的形式存储,如果不加转换的输出到外存的⽂件中,就是⼆进制⽂件。(数字)

2.文本文件
如果要求在外存上以ASCII码的形式存储,则需要在存储前转换。以ASCII字符的形式存储的⽂件就是⽂本⽂件。(即以字符串的方式存储)

例如:
整数10000
以文本文件存储就是字符'1'与四个字符'0'。
以二进制文件存储则是10000的二进制表示(整型,4个字节)。

文件的打开与关闭:

1.流

我们程序的数据需要输出到各种外部设备,也需要从外部设备获取数据,不同的外部设备的输⼊输出 操作各不相同,为了⽅便程序员对各种设备进⾏⽅便的操作,我们抽象出了流的概念,我们可以把流 想象成流淌着字符的河。 C程序针对⽂件、画⾯、键盘等的数据输⼊输出操作都是通过流操作的。 ⼀般情况下,我们要想向流⾥写数据,或者从流中读取数据,都是要打开流,然后操作。

2.标准流

那为什么我们从键盘输⼊数据,向屏幕上输出数据,并没有打开流呢?
那是因为C语⾔程序在启动的时候,默认打开了3个流:
• stdin - 标准输⼊流,在⼤多数的环境中从键盘输⼊,scanf函数就是从标准输⼊流中读取数据。
• stdout - 标准输出流,⼤多数的环境中输出⾄显⽰器界⾯,printf函数就是将信息输出到标准输出
流中。
• stderr - 标准错误流,⼤多数环境中输出到显⽰器界⾯。
这是默认打开了这三个流,我们使⽤scanf、printf等函数就可以直接进⾏输⼊输出操作的。
stdin、stdout、stderr 三个流的类型是: FILE* ,通常称为⽂件指针。
C语⾔中,就是通过 FILE* 的⽂件指针来维护流的各种操作的。

3.文件指针

写法为FILE * ptr,FILE*为文件指针类型。
通过⽂件指针变量能够间接找到与它关联的⽂件。

4.文件的打开与关闭

⽂件在读写之前应该先打开⽂件,在使⽤结束之后应该关闭⽂件。
在编写程序的时候,在打开⽂件的同时,都会返回⼀个FILE*的指针变量指向该⽂件,也相当于建⽴了 指针和⽂件的关系。
ANSI C 规定使⽤ fopen 函数来打开⽂件, fclose 来关闭⽂件。

filename为文件名字,stream为文件地址。
这里我们先展示一下两种mode

5.文件的读写函数:

我们可以来对比一下这两组函数;

fprintf(FILE* stream,const char * format,.......);

(适用于所有输出流)

fscanf(FILE* stream,const char * format,.......);

(适用于所有输入流)

sprintf(char * str,const char * format,......);

sscanf(char * str,const char * format,......)

这些之间的区别为:

printf和sacnf为在面板上输出与获取值。

fprintf/fscanf为在printf/scanf前加上文件地址,使其输出与输入在某个文件上执行。

sprintf/sscanf为加上字符数组地址,使得输入与输出均在某个字符数组上执行(输入与输出均自动转变为字符类型)。

中间的format为"%s %d"这种。

size_t fwrite(const void* ptr,size_t size,size_t count,FILE* stream)

以二进制的形式写入文件,读取也需要以二进制形式读取。

ptr为起始地址,size为单个元素所占字节大小,count为元素个数,stream为文件地址。

返回值为成功写入的元素个数。

size_t fread(void* ptr,size_t size,size_t count,FILE* stream),以二进制形式读取文件内容并放入ptr中。

返回值为成功读取的元素个数。

int feek(FILE* stream,long int offset,int origin)

根据⽂件指针的位置和偏移量来定位⽂件指针。

offset 偏移量

origin 起始位置

origin可供参数:

1.SEEK_SET:文件起始位置。2.SEEK_CUR:文件指针当前位置。3.SEEK_END:文件末尾(最后一个元素后一个位置)。

long int ftell(FILE*stream)

返回文件指针相对于起始位置的偏移量。

void rewind(FILE* stream)使指针回到文件起始位置。

文件读取结束的判定:

打开一个流的时候,这个流上有两个标记值:

1.是否与到文件末尾。

2.读取时是否发生错误。

int feof(FILE* stream)

判断流上是否有末尾标记,没有标记则返回0,有标记则不为0.

int ferror(FILE* stream)

判断流上是否有错误标记,没有标记则返回0,有标记则不为0.

牢记:

在文件读取的过程中,不能用feof函数的返回值直接来判断文件是否结束。

feof的作用是:当文件读取结束的时候,判断读取结束的原因是否是:遇到文件尾结束。

1.文本文件读取是否结束,判断返回值是否为EOF(fgetc)或NULL(fgets)

2.二进制文件的读取结束判断:判断返回值是否小于实际要读的个数。

例如:

fread判断返回值是否小于实际要读的个数。

文件缓冲区系统:

系统自动在内存中微程序每一个正在使用的文件开辟一块文件缓冲区。无论是从内存向磁盘输出数

据还是从磁盘向内存读取数据到内存都要经过缓冲区,分别为输出缓冲区与输入缓冲区。

流程为:程序数据区->输出缓冲区->硬盘->输入缓冲区->程序数据区

当缓冲区填满后才会将数据一起从到硬盘或磁盘上。

以下为案例:

这⾥可以得出⼀个结论:
因为有缓冲区的存在,C语⾔在操作⽂件的时候,需要做刷新缓冲区或者在⽂件操作结束的时候关闭⽂ 件。
如果不做,可能导致读写⽂件的问题。

相关推荐
l1t36 分钟前
利用DeepSeek实现服务器客户端模式的DuckDB原型
服务器·c语言·数据库·人工智能·postgresql·协议·duckdb
l1t3 小时前
利用美团龙猫用libxml2编写XML转CSV文件C程序
xml·c语言·libxml2·解析器
Hello_Embed3 小时前
STM32HAL 快速入门(二十):UART 中断改进 —— 环形缓冲区解决数据丢失
笔记·stm32·单片机·学习·嵌入式软件
咸甜适中4 小时前
rust语言 (1.88) 学习笔记:客户端和服务器端同在一个项目中
笔记·学习·rust
Magnetic_h5 小时前
【iOS】设计模式复习
笔记·学习·ios·设计模式·objective-c·cocoa
研梦非凡5 小时前
ICCV 2025|从粗到细:用于高效3D高斯溅射的可学习离散小波变换
人工智能·深度学习·学习·3d
limengshi1383926 小时前
机器学习面试:请介绍几种常用的学习率衰减方式
人工智能·学习·机器学习
知识分享小能手6 小时前
React学习教程,从入门到精通,React 组件核心语法知识点详解(类组件体系)(19)
前端·javascript·vue.js·学习·react.js·react·anti-design-vue
周周记笔记8 小时前
学习笔记:第一个Python程序
笔记·学习
优雅鹅8 小时前
ARM、AArch64、amd64、x86_64、x86有什么区别?
arm开发·学习