Day 31 C语言文件基础 (fprintf fscanf rewind ftell fseek ) 重定向

本文详细介绍了C语言中文件操作的基础知识,包括fprintf用于向文件写入数据、fscanf从文件读取数据、rewind将文件指针移回文件开头等函数的使用方法。此外还探讨了ftell获取文件当前位置、fseek改变文件位置的功能,并通过实例展示了如何利用这些函数实现文件内容的修改。
摘要由CSDN通过智能技术生成

fprintf

fprintf 是将源文件内的数据打印到文件中去

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

返回值

如果成功,则返回写入的字符总数,否则返回一个负数

fscanf

fscanf是将文件的内容读取,然后给源文件的变量

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

返回值

如果成功,该函数返回成功匹配和赋值的个数。如果到达文件末尾或发生读错误,则返回 EOF

rewind

rewind是将光标移到文件开始的地方

我们对文件写操作的时候,往往光标就移到了文件末尾,如果不用这个可能再次读就读不到

void rewind(FILE *stream)

ftell

ftell是返回从光标到文件开头之间的字节数

long int ftell(FILE *stream)

返回值

该函数返回位置标识符的当前值。如果发生错误,则返回 -1L,全局变量 errno 被设置为一个正值

fseek

是将光标移动到想要的位置

这样我们就可以对文件进行修改了,找到该位置,用fputs函数就可以将原来位置的内容进行替换,但我觉得这样是不保险的,因为字长要一样,要不然可能会出现错误的数据,以后应该会学到更好的方法

int fseek(FILE *stream, long int offset, int whence)

返回值

如果成功,则该函数返回零,否则返回非零值

这里我定义了一个结构体,将结构体的内容通过fprintf打印到文件中,再将文件中的内容读取到定义的另一个结构体数组中,在终端打印出来

用ftell看文件有多少个字节的内容

然后用fseek将第一条信息的名字做修改

#include<stdio.h>
typedef struct
{
	int id;
	char name[20];
	float score;
	char sex;
}MSG;

int main()
{	
	MSG msg[4] = {{1001, "陈奕迅", 96.5, 'm'},
				  {1002, "林俊杰", 97.7, 'm'},
				  {1003, "蔡依林", 98.5, 'f'},
				  {1004, "田馥甄", 87.5, 'f'}};
//	int id = 1001;
//	char name[20] = "周杰伦";
//	float score = 92.5;
//	char sex = 'm';
	FILE *fp = fopen("./1.txt", "r+");
	if(fp == NULL)
	{
		perror("Error");
	}
	MSG r_msg[4];
	for(int i = 0; i < 4; i++)
	fprintf(fp, "%d %s %.1f %c\n", msg[i].id, msg[i].name, msg[i].score, msg[i].sex);
	rewind(fp);
	for(int i = 0; i < 4; i++)
	fscanf(fp, "%d %s %f %c", &r_msg[i].id, r_msg[i].name, &r_msg[i].score, &r_msg[i].sex);
	for(int i = 0; i < 4; i++)
	printf("%d, %s, %.1f, %c\n", r_msg[i].id, r_msg[i].name, r_msg[i].score, r_msg[i].sex);
	
	long ret = ftell(fp);//返回从光标位置到文件起始位置的字节数 
	printf("%ld\n", ret);
	
	fseek(fp, 5, SEEK_SET);
	fputs("周杰伦", fp); 
	
	return 0;
}

重定向

重定向,通俗的来讲就是通过运用freopen函数将本该给终端打印的内容,打进了文件中,像这样做,就用stdout标准输出来控制;也可以用freopen函数将文件的内容,copy到数组中然后在终端输出

freopen

FILE *freopen(const char *filename, const char *mode, FILE *stream)
	FILE *fp = freopen("stdout.txt", "w", stdout);

中间的mode和之前打开文件的mode一样

"r"打开一个用于读取的文件。该文件必须存在。
"w"创建一个用于写入的空文件。如果文件名称与已存在的文件相同,则会删除已有文件的内容,文件被视为一个新的空文件。
"a"追加到一个文件。写操作向文件末尾追加数据。如果文件不存在,则创建文件。
"r+"打开一个用于更新的文件,可读取也可写入。该文件必须存在。
"w+"创建一个用于读写的空文件。
"a+"打开一个用于读取和追加的文件。

stream -- 这是指向 FILE 对象的指针,该 FILE 对象标识了要被重新打开的流,stdout、stdin、stderror

也可以在中途关掉这个被打开的流

例如你在重定向的时候用的是stdout,可以在代码中加入fclose(stdout),这样你做的输出操作就和文件没有什么交互了,也不可以正常的在终端输出,文件也不会保存输出内容,这样关的不太彻底,用下面的方法就可以彻底把freopen关掉了

freopen("CON", "w", stdout);

用了这个可以正常在屏幕上打印内容了 

#include<stdio.h>

int main()
{
	FILE *fp = freopen("stdout.txt", "w", stdout);
	if(fp == NULL)
	{
		perror("Error");
	}
	puts("a");
	puts("b");
	fclose(stdout);
	puts("c");
	puts("d");
	freopen("CON", "w", stdout);
	puts("1");
	puts("2");
	fclose(fp);

    return 0;
}

这样文件中就有了a b 1 2这四个数据,而c d不会保存到文件中;

下来可以使用freopen将文件内容读取,然后保存到数组中,然后再终端输出这个数组

#include<stdio.h>

int main()
{

	FILE *fp = freopen("stdin.txt", "r", stdin);
	if(fp == NULL)
	perror("Error");
	char name[30];
	fgets(name, 100, fp);
	puts(name);	
	return 0;
}

记得,用写到文件的时候用w,用读文件内容的时候用r

总结:

这两天讲的文件,内容不难,但是那些读取文件模式了解的有点少,他们之间的联系和区别都有什么,这些可能有些薄弱,需要再加强一下

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值