一、使用规则
1.需要包含<fstream>头文件
2.使用后记得及时关闭文件,以免造成资源浪费
3.文件分为:文本文件、二进制文件,按需选择
二、文件访问方式
方式 | 解释 |
ios::in | 读取文件内容 |
ios::out | 将内容写入文件 |
ios::ate | 定位到文件尾部 |
ios::app | 追加内容 |
ios::trunc | 如果文件存在,则删除后重建 |
ios::binary | 二进制数据 |
访问方式可以彼此搭配使用,两种方式中间用位或|符号连接。比如以下例子:
ofs.open("data.txt", ios::binary|ios::out);
三、读取文本文件
3.1 使用方法
采用ifstream对象,具体使用方法如下:
#include <fstream>
using namespace std;
int main() {
iftream ifs;
ifs.open("读入文件的目录", ios::in);
/***********读取数据*************/
/*这里对应四种读取方式,下边会介绍*/
/*******************************/
ifs.close();
return 0;
}
3.2 四种读取方式(推荐第三种)
为了方便说明,我们提前拥有一个名为data0.txt的文本文件,内容如下:
ABCD
Hello!Jacker
Hello, C++
3.2.1 第一种:流读取
ifstream ifs;
ifs.open("./data0.txt", ios::in);
//方式1:流读取
char buf[1024] = {};
while (ifs >> buf) {
cout << buf << endl;
}
ifs.close();
内容从文件最开始的位置读入,每次读取两个空白符号之间的内容,这里的空白符号是指:回车、空格、Tab、文件开端、文件结尾。程序执行效果如下:
3.2.2 第二种:行读取
ifstream ifs;
ifs.open("./data0.txt", ios::in);
//方式2:行读取
char buf[1024] = {};
while(ifs.getline(buf, sizeof(buf))) {
cout << buf << endl;
}
ifs.close();
内容也是从最开始读取,每次读取一行的数据(也就是读取两个换行符之间的内容)。
getline()函数有两个参数,第一个是缓冲器地址,第二个是缓冲区最大长度,程序执行结果如下:
注意:这里的getline()函数是ifs的一个成员函数。
3.2.3 第三种:字符串读取
ifstream ifs;
ifs.open("./data0.txt", ios::in);
//方式3:字符串读取
string strBuf;
while(getline(ifs, strBuf)) {
cout << strBuf << endl;
}
ifs.close();
这种方式也是从开始位置读取,将文件的内容一行一行地读入指定的string变量中。getline(ifstream, string)函数有两个参数,第一个参数是ifs对象,第二个是预设的string变量。
注意:这里的getline()函数不同于第二种方式,是一个全局函数,第二种是一个成员函数。
程序执行结果如下:
3.2.4 第四种:字符读取
ifstream ifs;
ifs.open("./data0.txt", ios::in);
//方式4
char item;
while( (item = ifs.get()) != EOF ) {
cout << '[' << item << ']' << endl;
}
ifs.close();
get()函数是ifs的一个成员函数,EOF(end of file)指的是文件结尾标志(EOF实际的值是-1)。
item = ifs.getc()返回的值是左值,也就是get()获取的ASCII值。如果不是文件结尾,当前读取到的字符的ASCII值一定是≥0的。因此可以通过以上方式,判断是否已经读取到文件结尾。
程序的执行结果如下:
四、写入文本文件
4.1 清空写入
访问方式选用ios::out,会将文件内容清空后,再写入指定内容。
#include <iostream>
#include <fstream>
using namespace std;
int main() {
ofstream ofs;
ofs.open("data0.txt", ios::out);
ofs << "Hello,File." << endl;
ofs << "Hello, Jacker" << endl;
ofs.close();
return 0;
}
4.2 追加写入
访问方式选用ios::app,会将文件结尾追加指定内容。
#include <iostream>
#include <fstream>
using namespace std;
int main() {
ofstream ofs;
ofs.open("data0.txt", ios::app);
ofs << "ABCDEFG" << endl;
ofs.close();
return 0;
}
五、写入二进制文件
注意:二进制文件虽然难以用肉眼解释,它的优势在于可以读写自定义类型的内容!
访问方式使用ios::out | ios::binary
#include <iostream>
#include <string>
#include <fstream>
using namespace std;
class Student{
public :
string name;
int age;
Student(string n = "XXX", int a = 0) : name(n), age(a) {}
void show() {
cout << name << "今年" << age << "岁" << endl;
}
};
int main() {
ofstream ofs;
Student stu("Daniel", 16);
ofs.open("./data2.txt", ios::out | ios::binary);
//这里需要将stu对象的地址强制类型转换为const char *类型,才符合write第一个参数类型
ofs.write((const char *)&stu, sizeof(stu));
ofs.close();
}
由于二进制写入的数据是0-1串,因此用文本编辑器打开后可能显示的是乱码,这里不用担心,我们想验证写入是否成功,只需要按照二进制的方式将文件内容读取到指定类型,再检验类型对象的值是否正确即可。
六、读取二进制文件
访问方式使用ios::in | ios::binary
#include <iostream>
#include <string>
#include <fstream>
using namespace std;
class Student{
public :
string name;
int age;
Student(string n = "XXX", int a = 0) : name(n), age(a) {}
void show() {
cout << name << "今年" << age << "岁" << endl;
}
};
int main() {
Student stu0;
ifstream ifs;
ifs.open("./data2.txt", ios::in | ios::binary);
cout << "读入前:" << endl;
stu0.show();
ifs.read((char *)&stu0, sizeof(stu0));
cout << "读入后:" << endl;
stu0.show();
ifs.close();
}
程序执行的结果为: