C/C++程序从文本文件中读取(保存)数据
:本文仅供初学者参阅,解惑
- 在C程序中:
与程序代码外的数据(文件)打交道,我们使用到流(stream)这个概念,实现进程的虚拟内存与文件之间的数据交换。
——文件流:C标准库提供了FILE(之所以命名为FILE,因为linux将所有机制都视为文件) ,FILE对象是一个包含了管理流所需的所有信息的结构,包括缓冲区信息、各种标记(如文件结束标记和错误标记)以及用于实际I/O的文 件描述符等。
——输入流,输入流:数据从文件传送到内存的叫输入流,数据从内存传送到文件的叫输出流。
——打开文件:FILE对象通过调用fopen函数创建的。如: FILE *fp, fp=fopen("filename","r"), 表示以只读的方式建立与filename相关的文件流;filename为当前目录下的相对路径名,r代表可读(打开文件的模式)。
一:读取
1:对一些有规范格式文件的读取,可使用标准库stdio.h下的fscanf函数,
函数原型为:int fscanf(FILE * stream, const char * format, [argument...])
如读取文件data.txt(数据格式相对规范)

代码实现读取:
//test.c
//文件读取
#include<stdio.h> int main()
{
//1:创建文件流,文件指针名=fopen(文件名,使用文件方式)打开失败则返回NULL;
FILE *fp=fopen("./data.txt","r"); //以data.txt文件为例 //2:检测文件是否打开成功;
if(!fp){
printf("打开失败!\n");
return -; //返回异常
}
//3:
int num; //用来储存一个整型数据
char name[], place[]; //用来储存两个字符串数据 //抽象理解:
//理解文件位置含义:其表示已打开文件当前可读写字符的位置,其表示为一个到文件头的整数;
//fscanf在读取数据时可以这样理解:文件被打开后,它就成了一个无序字节流(水流),其会通过一个管道,流向被读取的一端;
//了解fscanf后知道,其遇到空格字符(空格,制表符),换行符,就会停止,这里的停止我们可以理解为:
//停下来为文件中两个不相关的数据块做一个分隔的操作,刚好适应了我们一般将空字符(包括换行符)作为两个数据之间的分隔的行为;
//我们只需理解管道的两端
//流进管道的一端的位置,就是文件的位置,表示已被读到的位置。
//流出管道一端,就是进程用来读取数据的一端,其可以对管道中已经做区分的数据进行读取。 //4:读取:
fscanf(fp,"%d%s%s",&num, name,place); //fscanf对流的格式化读取。
//注1:fscanf(fp,"%da%s%s",&num,name,place); 可以实现对数据:1a小刚 河南;的准确读取,表示两个数据之间以a为界。
//注2:因为流是指针的性质,所以函数是将各数据块的首地址交给对应参数,所以num需进行&取地址操作,
//注3:因为name,place本身已表达地址,所以不用改变; fscanf(fp,"\n");
//\n为控制字符,此时文件的位置到了第二行的开始; //接着进行操作:fscanf(fp,"%d%s%s",&num, name,place);就可以继续读取第二行
//所以我们常常只需利用一个while语句就可以将整个文件读取到一个数据结构(进程)中
/*
while(!feof(fp)) //feof()检测一个文件是否结束,即到达文件尾,若结束,则返回非0值,否则返回0
{
fscanf(fp,"%d%s%s\n",&num, name,place);
}
*/ //检测读取结果
printf("%d %s %s\n",num, name, place); //关闭流
fclose(fp); return ; }
程序运行结果:

2:从文件中读取整行数据(标准库stdio.h下的fgets)
函数原型:char *fgets(char *str, int n, FILE *stream);
其从指定的流 stream 读取一行,并把它存储在 str 所指向的字符串内。当读取 (n-1) 个字符时,或者读取到换行符时,或者到达文件末尾时,它会停止,遇到空格不停止;
例从文件中读取一行数据:

代码实现:
//test3.c
//行读取文件数据 #include<stdio.h>
#define maxlen 30 int main()
{
//创建文件流
FILE *fp=fopen("./data.txt","r"); //2:检测文件是否打开成功;
if(!fp){
printf("打开失败!\n");
return -; //返回异常
}
char str[maxlen];//缓冲区,用来储存数据 //从文件中读取一行数据,储存到str开始的地址,最大长度为maxlen,然后下次读取从下行开始
//如果该行的数据长于maxlen-1,则只能返回一个不完整的行,并下次调用时从该处开始
fgets(str,maxlen,fp); //检测结果
printf("%s\n",str); //关闭流
fclose(fp);
return ; }
运行结果:

二:保存
1:保存与读取往往相关联,保存格式决定了你读取的方式,使用函数fprintf可以进行指定格式的保存:
函数原型为:int fprintf( FILE *stream, const char *format, [ argument ]...)
假设保存一个人的个人信息到文件中:
/*test2.c */
//数据保存 #include<stdio.h> int main()
{
//例一个人的信息
int num=;
char name[]="小明";
char place[]="河南"; //建立与文件的流
FILE *fp=fopen("./data.txt","w"); //2:检测文件是否打开成功;
if(!fp){
printf("打开失败!\n");
return -; //返回异常
} //将数据格式化输出到指定文件流,int fprintf( FILE *stream, const char *format, [ argument ]...)
//注:此函数,是将format字符串写入到指定输出流中,format包括空格字符,非空格字符,说明符之中的一个或多个。如:fprintf(fp," "); 就是将空格输入到流中。
//可理解为进程借助流将数据打印(fprintf)到了文件中; //将个人信息,写入指定流中,数据间以一个空格分隔,最后还写入换行符(控制字符)。
fprintf(fp,"%d %s %s\n",num, name,place); //所以常常只要利用一个while语句就可以将讲一个表(链表,顺序表)按指定行格式写入输出流中
/*
while(!feof(fp)) //feof()检测一个文件是否结束,即到达文件尾,若结束,则返回非0值,否则返回0
{
fprintf(fp,"%d %s %s\n",num, name,place);
}
*/
//关闭流
fclose(fp); return ; }
运行结果:

2:写一个字符串到流中(fputs),函数原型:int fputs(const char *str, FILE *stream);
例:
//test4.c
//保存字符串 #include<stdio.h> int main()
{
//1:创建文件流,文件指针名=fopen(文件名,使用文件方式)打开失败则返回NULL;
FILE *fp=fopen("./data.txt","a"); //以data.txt文件为例,a表示追加 //2:检测文件是否打开成功;
if(!fp){
printf("打开失败!\n");
return -; //返回异常
} //string
char string[]="Facing the world"; //write string to the fstream
fputs(string,fp); //关闭流
fclose(fp); return ; }
运行结果:

浅谈c++:
在c++中我们可以使用操作符<<, >>来进行流的读写操作,更加的方便和易于理解;
具体参考下列实例:
1:读取所示数据:

代码实现:
//c++文件读取
#include<iostream> //输入输出流
#include<fstream> //文件流 //using namespace std; //若使用该声明,则可以不用在使用的每个标准库的成员前加std:: int main()
{
//序号,年龄,年;
int num, age, year;
//姓名,地址
char name[], place[]; //c++的文件流,ifstream为输入文件流
std::ifstream fp; //open为ifstream的成员函数,功能为打开文件,并将它与流关联
fp.open("./data.txt",std::ios::in); //ios::in表示读流的方式,表示打开模式。 //成员函数is_open检查流是否有关联文件,即打开成功与否,成功返回true,失败返回false
if(!fp.is_open()){
std::cout<<"打开文件失败!!\n";
return ; // 返回异常;
} //读取数据
fp>>num>>year>>age>>name>>place; //使用操作符>>,将数据传输到对应的变量中 //检测
std::cout<<num<<":"<<name<<",age:"<<age<<",year:"<<year<<",live in:"<<place<<"\n"; //cout相当于printf //关闭流
fp.close(); return ;
}
运行结果:

2:往文件保存数据:
实例:保存一个人的具体信息到文件data.txt中

代码实现:
//c++数据保存
#include<iostream> //输入输出流
#include<fstream> //文件流 //using namespace std; //若使用该声明,则可以不用在使用的每个标准库的成员前加std:: int main()
{
//序号,年龄,年;
int num=;
int age=;
int year=;
//姓名,地址
char name[]="小龙";
char place[]="广元"; //c++的文件流,ofstream为输出文件流
std::ofstream fp; //open为ofstream的成员函数,功能为打开文件,并将它与流关联
fp.open("./data.txt",std::ios::app); //ios::app表示每次写入是都追加到流尾,表示打开模式。 //成员函数is_open检查流是否有关联文件,即打开成功与否,成功返回true,失败返回false
if(!fp.is_open()){
std::cout<<"打开文件失败!!\n";
return ; // 返回异常;
} //读取数据
fp<<num<<" "<<year<<" "<<age<<" "<<name<<" "<<place<<"\n"; //使用操作符<<,将各数据传输到流所关联的文件中 //关闭流
fp.close(); return ;
}
运行结果:

C/C++程序从文本文件中读取(保存)数据的更多相关文章
- java算法面试题:从类似如下的文本文件中读取出所有的姓名,并打印出重复的姓名和重复的次数,并按重复次数排序 ;读取docx 读取doc 使用poi 相关jar包提集提供下载
从类似如下的文本文件中读取出所有的姓名,并打印出重复的姓名和重复的次数,并按重复次数排序 1,张三,28 2,李四,35 3,张三,28 4,王五,35 5,张三,28 6,李四,35 7,赵六,28 ...
- ML.NET Cookbook --- 1.如何从文本文件中加载数据?
使用ML.NET中的TextLoader扩展方法从文本文件中加载数据.你需要知道在文本文件中数据列在那里,它们的类型是什么,在文本文件中什么位置可以找到它们. 请注意:对于ML.NET只读取文件的某些 ...
- matlab中读取txt数据文件(txt文本文档)
matlab中读取txt数据文件(txt文本文档) 根据txt文档不同种类介绍不同的读取数据方法 一.纯数据文件(没有字母和中文,纯数字) 对于这种txt文档,从matalb中读取就简单多了 例如te ...
- 如何实现MySQL表数据随机读取?从mysql表中读取随机数据
文章转自 http://blog.efbase.org/2006/10/16/244/如何实现MySQL表数据随机读取?从mysql表中读取随机数据?以前在群里讨论过这个问题,比较的有意思.mysql ...
- C# 操作地址 从内存中读取写入数据(初级)
本示例以植物大战僵尸为例, 实现功能为 每1秒让阳光刷新为 9999.本示例使用的游戏版本为 [植物大战僵尸2010年度版], 使用的辅助查看内存地址的工具是 CE. 由于每次启动游戏, 游戏中阳光 ...
- python中读取mongodb数据并保存为csv格式的文件
import pandas as pd import matplotlib.pyplot as plt import pymongo %matplotlib inline # 连接mongodb数据库 ...
- c++从文件中读取一行数据并保存在数组中
从txt文本中读取数据存入数组中 #include <iostream> #include <fstream> #include <string> #include ...
- matlab中读取txt数据文件(转)
根据txt文档不同种类介绍不同的读取数据方法 一.纯数据文件(没有字母和中文,纯数字) 对于这种txt文档,从matalb中读取就简单多了 例如test.txt文件,内容为“17.901 -1.111 ...
- 以ORM的思路来从Excel文件中读取JSON数据列表
1.一个常见的问题就是如何读取excel. 这里面有几个分支的问题,一个是如何使用poi读取excel,网上例子很多,但是这只解决了第一步.如何将excel读取入一定的数据结构这是第二个问题,还有就是 ...
随机推荐
- C++的多态总结(静态&动态)
什么是多态 顾名思义就是同一个事物在不同场景下的多种形态. 静态多态 我们以前说过的函数重载就是一个简单的静态多态,静态多态是编译器在编译期间完成的,编译器会根据实参类型来选择调用合适的函数,如果有合 ...
- Web服务与应用
一.Apache 1.1 简介 Apache是一个高稳定,商业级别开源的Web服务器 1.2 下载镜像 DockerHub官方提供Apache镜像不带PHP环境,也就是不是动态网页页面,只能生成静态的 ...
- Python | 字符串拆分和拼接及常用操作
一.字符串拆分 str = "hola ha1 ha2 china ha3 " # partition 从左侧找到第一个目标,切割成三组数据的[元组] str1 = str.par ...
- 阻塞队列BlockingQueue之ASynchronousQueue
一.SynchronousQueue简介 Java 6的并发编程包中的SynchronousQueue是一个没有数据缓冲的BlockingQueue,生产者线程对其的插入操作put必须等待消费者的移除 ...
- js的变量(01)
变量的声明用的修饰符 var ,let ,const var是普通变量 var 变量名 = 变量值 可以重复定义可以多次修改 let是es6新加的语法 let 变量 ...
- python文件读取:遇见的错误及解决办法
问题一: TypeError: 'str' object is not callable 产生原因: 该错误TypeError: 'str' object is not callable字面上意思:就 ...
- MySQL性能优化---优化方案
1.对查询进行优化,应尽量避免全表查询,首先考虑在where及order by涉及的列上建立索引: 2.应尽量避免where子句中对字段进行null值判断,否则将导致引擎放弃使用索引而进行全表扫描: ...
- C/C++内存四区
内存模型图 32位CPU可寻址4G线性空间,每个进程都有各自独立的4G逻辑地址,其中0~3G是用户态空间,3~4G是内核空间,不同进程相同的逻辑地址会映射到不同的物理地址中.其逻辑地址其划分如下: 各 ...
- 计算几何-Dot-Vector
This article is made by Jason-Cow.Welcome to reprint.But please post the article's address. 看了书,然后码 ...
- drf-jwt手动签发与校验,drf小组件:过滤、筛选、排序、分页
复习 """ 频率组件:限制接口的访问频率 源码分析:初始化方法.判断是否有权限方法.计数等待时间方法 自定义频率组件: class MyThrottle(SimpleR ...