测试必备技能之C语言文件函数(超级全能篇)——FILE函数

2023-05-16

之前出过的文件FILE函数的小白篇,现在出一个全面一些的
在这里插入图片描述

以下讲解直接分为函数原型+函数作用+测试用例
让大家真真正正的理解和感受这几个FILE函数的作用

二话不说,开冲!

额…先来个小表格:

在这里插入图片描述

在这里再重复一下上一篇讲述过的几个基本的FILE函数,由于这几个函数在上一个博客都有讲过,而且比较基础简单在这里就没有测试用例啦,直接简单看函数原型和作用☺☺☺
★fopen()函数

✿、函数原型:FILEfopen(charfilename,char*type);
✿、函数作用:
打开一个“流“

★fclose()函数

✿、函数原型:
int fclose(char*filename);
✿、函数作用:
关闭一个“流“

★fprintf()函数

✿、函数原型:
int fprintf(charfilename,charformat[,argument,…])(format就是要写入的参数)
✿、函数作用:
传送格式化文本形式输出到一个流中

好了,结束了上面几个在小白篇出现的三个常用FILE函数,让我们进入正题:

首先,在这里回答一个问题:

在开始接触FILE函数这一个模块的时候,先了解一下文件的类型,常见的有二进制类的,还有文本形式类的,怎么区分呢?

简记:一个是看不懂的文字,而一个是你看得懂的在这里插入图片描述
个人认为,言简意赅,十分易记

演示一波

二进制文件:
在这里插入图片描述
文本文件:
在这里插入图片描述
简单理解了之后,细细想想这两个到底有什么区别和差异,在这里我不多加赘述,这一篇是讲述FILE函数的,所以以下内容主要对我怎么写二进制文件、怎么写文本文件等等一系列操作进行函数剖析和演示,具体这两个形式有什么具体区别,我会在下一篇出♥♥♥♥♥


feof()函数
✿、函数原型:
int feof(FILE*stream);额…和前面区别一下嘛在这里插入图片描述
✿、功能:
检测流上的文件结束符
没有什么特别意思,就是检测到你的文件到末尾了,后面没有东西了♞
✿、程序用例:

#define _CRT_SECURE_NO_WARNINGS
#include<stdlib.h>
#include<stdio.h>
#include<string.h>
int main() {
	FILE* fp;
	fp = fopen("test.txt","r");
	char c = '0';//初始化中间变量
	if (fp == NULL)
	{
		printf("打开文件失败!\n");
		exit(0);
	}
	while (!feof(fp))//feof(fp)==NULL,代表已经结束,这句话非常常用
	{
		c=fgetc(fp);
		printf("%c\n",c);
	}

	if (feof(fp))
	{
		printf("We have reached the end!\n");
	}
	fclose(fp);
	return 0;
}

test.txt文件内容:
在这里插入图片描述
结果:
在这里插入图片描述
之前有些人有问到关于”空格“的问题,在这里大家可以放心,feof()函数它就是可以检测到这个文件到底有没有结束,就像这里我空了几个空格,它也会算进去的,不得不说,酷在这里插入图片描述


fgetc()函数
在上面的代码中,相信眼尖的小伙伴看到了这一句:
c=fgetc();
✿、函数原型:
int fgetc(FILE*stream);
✿、作用:
从流中读取字符(就是一个一个去读,及其好用)
✿、程序用例:
额…我写到这里我发现,咦?上面那个程序测试用例好像已经说明了这个函数的意思了
在这里插入图片描述
咳咳,那好吧,就再来其他的组合好了在这里插入图片描述


fgetchar ()、fputchar()、freopen()函数登场
✿、函数原型
int fgetchar(void);
int fputchar(char ch);
FILE *freopen(char *filename, char *type, FILE *stream);

✿、函数功能:
**fgetchar:从流中读取字符,fgetchar()其实它等价于fgetc(stdin),而且使用VS的朋友,怎么说呢,我记得好像在V C++2005年开始,fgetchar()这个函数已经被废弃了,要使用_fgetchar()代替使用,包括下面的fputchar也是前面要修改,具体看下案例代码
**fputchar:送一个字符到标准输出流(stdout)中
**freopen:将一个新的名为filename与给定的打开流stream关联,同时关闭流中的旧文件,在函数定义时的stream–它指的就是指向FILE对象的指针,该指针对象标识了要被重新打开的流

★stream常用三个值:
stdout(Standardoutput)标准输出
stdin(Standardinput)标准输入
stderr(Standarderror)标准错误

根据官网的解释就是:只是方便操作输出,比如传给一个函数等等。这时函数的输出就不是输出到文件,而是传进来的stdout文件指针,即标准输出。(stdout为例)

具体的用法如下:
✿、程序案例:

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

int main(void)
{
	int c;
	FILE* fp;
	fp = freopen("test.txt","r",stdin);
	if (fp != NULL)
	{
		while ((c = _fgetchar()) != EOF)//输入功能
		{
			_fputchar(c);//输出功能
		}
	}
	fclose(fp);
	return 0;
}

test文件:
在这里插入图片描述
结果:
在这里插入图片描述


现在不改变test文本内容,让我们看一看freopen()函数的“关联”特性,我们执行以下代码:

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

int main(void)
{
	FILE* fp;
	printf("----让文本重定向到 stdout测试---\n");
	fp = freopen("test.txt", "a+", stdout);
	printf("该文本重新定位到到 test.txt\n");
	printf("测试结束啦啦啦!");//输出变成到文件输出去了,控制台没有这一句输出了
	fclose(fp);
	return 0;
}


结果:
test.txt文件变成:
在这里插入图片描述
会发现只要使用了这个函数,它的意思就是你将你的输出就比如printf,大家都知道这个是直接输出到控制台的,可是会发现它在你的文件中输出了,有种重新指定的意味,它关联了你所指定的文件,这也是这个函数最重要的功能之一


fscanf()函数

✿、函数原型
int fscanf(FILE *stream, char *format[,argument…]);
✿、功能
从一个流中执行格式化输入
✿、程序案例:
额…先重现让test.txt文件恢复原样:
在这里插入图片描述
ok,继续

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

int main(void)
{
	FILE* fp;
	char c = '0';
	fp = fopen("test.txt", "r");
	while (!feof(fp))
	{
		fscanf_s(fp,"%c",&c,1);//1为缓冲区大小,就跟你用scanf_()一样
		printf("%c",c);
	}
	fclose(fp);
	return 0;
}

这个函数的作用就是跟scanf非常的像,就是简单的一个赋值的操作,也非常的常用
结果:
在这里插入图片描述
将文件中的东西通过赋值给c输出,这个函数较为简单,过过过


fwrite()函数和fread()函数姐妹花组合
前面讲的大部分用于文本文件,就比如fprintf()就是以格式化的数据写进去,fscanf_()也是一般用于文本的读取,那么对于二进制文件我们应该怎么处理呢?这两个函数便是主要用于处理二进制读写的函数

除此之外呢,这两个函数主要是读取“数据块”,看它的函数原型在这里插入图片描述

✿、函数原型
int fread(void *ptr, int size, int nitems, FILE *stream);
int fwrite(void *ptr, int size, int nitems, FILE *stream);
解释一下:
ptr指的就是表示存放输入数据的首地址(一般会用数组)
size是指数据块的字节数,nitems是指读取的数据块的个数
比如说:fread(arr,4,5,fp)意义就是从fp所指的文件中,每次读入4个字节送入到arr数组中,连续读五次
✿、功能
这两个函数相信大家字面意思也能懂了,就是一个读、一个写,就是这么狠在这里插入图片描述
具体看下在这里插入图片描述

而且而且大家一定要注意的是:在读写二进制文件时候,必须确保文件的打开形式是以二进制读写的形式打开的,即类似“rb”,"wb"等在这里插入图片描述

✿、程序案例:
举一个非常简单的例子
fwrite():

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


int main()
{
	FILE* fp;
	fp = fopen("test_1.data","rb+");
	int buf[40];
	char arr[40] = "\0";
	char c = '\0';
	int i = 0;
	if (fp == NULL)
	{
		printf("faile open the file\n");
		exit(0);
	}
	
	for (int i = 0; i < 5; i++)
	{
		scanf_s("%d",&buf[i]);
	}
	fwrite(buf,sizeof(int),5,fp);
	fclose(fp);
	return 0;
}

测试输入:10100
结果:在这里插入图片描述

乱码(字节大小:20(int是4,5个4=20))
在这里插入图片描述
就着上面已经有的这个二进制文件,我们用fread()函数去解读它:

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


int main()
{
	FILE* fp;
	fp = fopen("test_1.data","rb+");
	int buf[40];
	int arr[40];
	char c = '\0';
	int i = 0;

	fseek(fp,SEEK_SET,0);//从文本开头开始读取
	fread(arr,20,1,fp);

	for (int i = 0; i < 5; i++)
	{
		printf("%d",arr[i]);
	}

	fclose(fp);
	return 0;
}

结果:在这里插入图片描述
不得不说,强大在这里插入图片描述


fseek()函数
这个函数比较简单理解,就是规定文件指针位置,比如你不想每次都从文件首部开始,想从一个特定的位置开始,那么这个函数就是起到这样一个作用的
✿、函数原型
int fseek(FILE *stream, long offset, int fromwhere);
✿、功能
重新定义流上的文件指针
offset:相对于fromwhere的偏移,以字节为单位
fromwhere:偏移的位置
一般指定为下列三个常量之一:
SEEK_SET 文件的开头
SEEK_CUR 文件指针的当前位置
SEEK_END 文件的末尾

✿、程序案例
在这里插入图片描述

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


int main()
{
	FILE* fp;
	fp = fopen("test.txt","r");
	char c = '0';
	if (fp == NULL)
	{
		printf("fail open the file!\n");
		exit(0);
	}
	printf("现在从距离起点4个字节位置开始读取:\n");
	fseek(fp,4,SEEK_SET);
	while (!feof(fp))
	{
		fscanf_s(fp,"%c",&c,1);
		printf("%c",c);
	}
	fclose(fp);
	return 0;
}

结果:
在这里插入图片描述
基于这个函数比较简单,大家可以自己去玩一玩,在这里不赘述更多的测试用例了在这里插入图片描述


ftell()函数

✿、函数原型:
long ftell(FILE *stream);
✿、功能:
返回当前文件的指针(额…就是文件字节数啦)
✿、程序测试用例:

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


int main()
{
	FILE* stream;
	stream = fopen("test.txt", "w+");
	fprintf(stream, "This is a test");
	printf("The file pointer is at byte % ld\n", ftell(stream)); 
	fclose(stream);

	return 0;
}

结果:
在这里插入图片描述
在这里插入图片描述


fgets()函数
前面讲了fgetc()函数,现在来一个它的兄弟在这里插入图片描述
✿、函数原型:

char *fgets(char *string, int n, FILE *stream);
✿、功能
从流中读取字符串
✿、程序案例:

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


int main()
{
	FILE* stream;
	char string[] = "I am X BIG MONSTER";
	char msg[20];
	stream = fopen("test.txt", "w");
	fwrite(string, strlen(string), 1, stream);
	fseek(stream, 0, SEEK_SET);
	fgets(msg, strlen(string) + 1, stream);
	fclose(stream);


	return 0;
}

结果:
在这里插入图片描述

总结

还是那句话,自己多动手,就会发现奥妙之处在这里插入图片描述
可能不够完善,我会努力更哒在这里插入图片描述

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

测试必备技能之C语言文件函数(超级全能篇)——FILE函数 的相关文章

  • 如何打开 matlab p 代码文件

    有谁知道如何查看 matlab p 代码文件的代码 p 代码文件专门存在 以便您可以共享代码 以便其他人无法查看它 换句话说 您看不到 Matlab p 代码文件的代码
  • 在 C# 中创建文件的最快方法

    我正在运行一个程序来测试在包含大量文件的文件夹中查找和迭代所有文件的速度 该过程中最慢的部分是创建超过 100 万个文件 我目前正在使用一种非常幼稚的方法来创建文件 Console Write Creating 0 N0 file s of
  • 确定执行脚本的路径

    我有一个名为foo R其中包括另一个脚本other R 位于同一目录中 usr bin env Rscript message Hello source other R 但我想要R找到那个other R无论当前工作目录是什么 换句话说 fo
  • CMake:将为 lib 构建的对象文件重用到另一个 lib 目标中

    我正在尝试将我的项目转移到CMake 同时对编译过程进行一些优化 这是交易 我有几个子目录 必须 每个子目录都编译成静态库 这有效 我想将每个子目录中的所有目标文件收集到另一个更大的 完整的静态库中 它看起来像这样 libBig a mad
  • 向每个表格单元格添加进度条以显示文件进度 - Java

    当您单击 加密 时 应用程序会对放入表中的每个文件进行加密 我想显示文件加密时的进度 然后 状态 列将从 未处理 更改为 已处理 类似于您查看电子邮件中附加的多个文件的方式 我一直在研究单元格渲染器和 ProgressBarTablecel
  • 在Android上保存文件时避免因中断而丢失数据?

    我想知道其他人在 Android 上保存文件时使用什么策略来避免数据丢失 我有几个游戏应用程序 本质上 它们可能会在用户暂停 onPause 时保存游戏状态 保存游戏 这在 99 99 的情况下有效 但每隔一段时间我就会收到一个保存游戏的例
  • 将一个文件写入.c中的另一个文件

    我有一个读取文件然后将其内容复制到另一个文件的代码 我需要使其仅复制每 20 个符号 然后跳过 10 个符号 然后再次跳过 20 个符号 依此类推 我必须使用 lseek 函数 但我不知道如何将所有这些放入循环中来执行此操作 main ar
  • 如何用php将文件内容转换为字节数组

    我想用PHP将上传的文件保存 插入 到数据库中 数据库字段的类型是varbinary 最后 我想要获得 VarBinary 输出 的内容 就像在 C 中读取文件然后将其存储在字节数组中并将数组插入到 VarBinary 中一样 我与数据库的
  • 在 Java 中打开现有文件并关闭它。

    是否可以在java中打开一个文件附加数据并关闭多次 例如 psuedocode class variable declaration FileWriter writer1 new FileWriter filename fn1 writer
  • QT 中只获取文件而不获取目录?

    当我这样做时 QDir myDir home some location QStringList filesList myDir entryList 它返回该位置内的文件和目录 但我只想要文件 并且这些文件可以具有任意扩展名 有任何想法吗
  • 如何在as3中不询问的情况下写入外部文件

    我有这个代码 var fileRef FileReference new FileReference fileRef save ciao coso lingua txt 在现有的 lingua txt 文件上写入 该脚本有效 但每次他保存时
  • C++ 输出到文本文件时换行符[关闭]

    很难说出这里问的是什么 这个问题是含糊的 模糊的 不完整的 过于宽泛的或修辞性的 无法以目前的形式得到合理的回答 如需帮助澄清此问题以便重新打开 访问帮助中心 help reopen questions 这只是一个简单的问题 但我正在尝试将
  • 读取FCS文件

    我正在研究流式细胞术 我想使用 python 解析 fcs 文件 我在互联网上研究过 有一个模块fcm但这是针对Linux操作系统的 我正在Windows上工作 我想知道如何使用 python 解析 Windows 中的 fcs 文件 如果
  • 从文件中读取未知长度的int数组

    如何从文件中读取未知长度的整数数组 我没有找到获取数组大小的方法 所以我尝试了一些临时字符串的东西 但我的代码爆炸了 有更好的想法吗 Use std vector std ifstream inFile fileName std vecto
  • 视图无法解析为类型

    这里的视图似乎有什么问题 我该如何解决它 错误 视图无法解析为类型 public void onItemClick AdapterView
  • 从文本文件 PHP 读取数据

    我只是想知道如何在 php 中读取文本文件 我想让它显示文本文件中的最后 200 个条目 每个条目都在一个新行上 Like John White Jane Does John Does Someones Name 等等 Thanks Use
  • 如何根据扩展名获取文件类型信息? (不是 MIME)在 c# 中

    如何获取基于扩展名的一般文件类型描述 如资源管理器 所以不是 MIME 而是最终用户看到的信息 doc Microsoft Office Word 97 2003 文档 zip ZIP 文件 avi 视频文件 我怎样才能获得似乎可用的 辅助
  • 将ADODB二进制流转换为字符串vba

    我有以下问题 我有一个存储在服务器上的 CSV 文件 但它有 3 个字符作为分隔符 我想从 URL 加载数据并使用 作为分隔符将数据填充到 Excel 页面的列中 到目前为止 我找到了使用 ADODB 记录集从网站加载文件的代码 但我无法进
  • 在 Java(TM) Platform SE 二进制文件中打开

    我尝试删除一个文件 其中有两个文件 其中一个略有更改 因此我可以删除旧文件并将其替换为我更改的新文件 当我尝试删除该文件时 收到错误消息 文件正在使用 其中表示该操作无法完成 因为该文件是在 Java TM Platform SE 二进制文
  • 如何使用 Oracle 移动文本文件

    我有两个问题 1 如何从文件夹中移动文本文件 C Data inbox test txt 目标文件夹 C Data outbox test txt 2 如何获取文件夹中的目录文件列表 C Data inbox 谢谢 Oracle 提供了一个

随机推荐