第十天之文件流类和文件流对象

文件流类和文件流对象

输入输出是以系统指定的标准设备(输入设备为键盘,输出设备为显示器)为对象的。在实
际应用中,常以磁盘文件作为对象。即从磁盘文件读取数据,将数据输出到磁盘文件。
和文件有关系的输入输出类主要在 fstream.h 这个头文件中被定义,在这个头文件中主要被
定义了三个类,由这三个类控制对文件的各种输入输出操 作,他们分别是 ifstream、ofstream、
fstream,其中 fstream 类是由 iostream 类派生而来,他们之间的继承关系见下图所 示。
在这里插入图片描述
由于文件设备并不像显示器屏幕与键盘那样是标准默认设备,所以它在 fstream.h 头文件中
是没有像 cout 那样预先定义的全局对象,所以我们必须自己定义一个该类的对象。
ifstream 类,它是从 istream 类派生的,用来支持从磁盘文件的输入。
ofstream 类,它是从 ostream 类派生的,用来支持向磁盘文件的输出。
fstream 类,它是从 iostream 类派生的,用来支持对磁盘文件的输入输出。

C++文件的打开与关闭

所谓打开(open)文件是一种形象的说法,如同打开房门就可以进入房间活动一样。 打开文
件是指在文件读写之前做必要的准备工作,包括:
1)为文件流对象和指定的磁盘文件建立关联,以便使文件流流向指定的磁盘文件。
2)指定文件的工作方式,如,该文件是作为输入文件还是输出文件,是 ASCII 文件还是二
进制文件等。
以上工作可以通过两种不同的方法实现。

  1. 调用文件流的成员函数 open。如
    ofstream outfile; //定义 ofstream 类(输出文件流类)对象 outfile
    outfile.open(“f1.dat”,ios::out); //使文件流与 f1.dat 文件建立关联
    第 2 行是调用输出文件流的成员函数 open 打开磁盘文件 f1.dat,并指定它为输出文件, 文
    件流对象 outfile 将向磁盘文件 f1.dat 输出数据。ios::out 是 I/O 模式的一种,表示以输出方
    式打开一个文件。或者简单地说,此时 f1.dat 是一个输出文件,接收从内存输出的数据。
    调用成员函数 open 的一般形式为:
    文件流对象.open(磁盘文件名, 输入输出方式);
    磁盘文件名可以包括路径,如"c:\new\f1.dat",如缺省路径,则默认为当前目录下的文件。
  2. 在定义文件流对象时指定参数
    在声明文件流类时定义了带参数的构造函数,其中包含了打开磁盘文件的功能。因此,可以
    在定义文件流对象时指定参数,调用文件流类的构造函数来实现打开文件的功能。如
    ostream outfile(“f1.dat”,ios::out); 一般多用此形式,比较方便。作用与 open 函数相同。
    输入输出方式是在 ios 类中定义的,它们是枚举常量,有多种选择,见表 13.6。
    在这里插入图片描述
    几点说明:
  3. 新版本的 I/O 类库中不提供 ios::nocreate 和 ios::noreplace。
  4. 每一个打开的文件都有一个文件指针,该指针的初始位置由 I/O 方式指定,每次读写都
    从文件指针的当前位置开始。每读入一个字节,指针就后移一个字节。当文 件指针移到最
    后,就会遇到文件结束 EOF(文件结束符也占一个字节,其值为-1),此时流对象的成员函数
    eof 的值为非 0 值(一般设为 1),表示文件结束 了。
  5. 可以用“位或”运算符“|”对输入输出方式进行组合,如表 13.6 中最后 3 行所示那样。还可
    以举出下面一些例子:
    ios::in | ios:: noreplace //打开一个输入文件,若文件不存在则返回打开失败的信息
    ios::app | ios::nocreate //打开一个输出文件,在文件尾接着写数据,若文件不存在,则
    返回打开失败的信息
    ios::out l ios::noreplace //打开一个新文件作为输出文件,如果文件已存在则返回打开失
    败的信息
    ios::in l ios::out I ios::binary //打开一个二进制文件,可读可写
    但不能组合互相排斥的方式,如 ios::nocreate l ios::noreplace。
  6. 如果打开操作失败,open 函数的返回值为 0(假),如果是用调用构造函数的方式打开文件
    的,则流对象的值为 0。可以据此测试打开是否成功。如
    if(outfile.open(“f1.bat”, ios::app) ==0)
    cout <<“open error”;

    if( !outfile.open(“f1.bat”, ios::app) )
    cout <<“open error”;

关闭文件

在对已打开的磁盘文件的读写操作完成后,应关闭该文件。关闭文件用成员函数 close。如
outfile.close( ); //将输出文件流所关联的磁盘文件关闭
所谓关闭,实际上是解除该磁盘文件与文件流的关联,原来设置的工作方式也失效,这样,
就不能再通过文件流对该文件进行输入或输出。此时可以将文件流与其他磁盘文件建立关联,
通过文件流对新的文件进行输入或输出。如
outfile.open(“f2.dat”,ios::app|ios::nocreate);
此时文件流 outfile 与 f2.dat 建立关联,并指定了 f2.dat 的工作方式。

案例一:


#include<iostream>
#include"fstream"
#include <iomanip>
using namespace std;

void main()
{
	char *fname = "e:/2.txt";
	ofstream fout(fname, ios::app);	//建一个输出流和文件进行关联,输出流就相当于文件了 ios::app以追加的方式打开
	if (!fout)
	{
		cout << "打开文件失败" << endl;
	}
	fout << "yangyun" << endl;
	fout << "lijiatu" << endl;
	fout.close();	//关闭流

	//读文件
	ifstream fin(fname);	//建了一个输入流
	char ch;
	while (fin.get(ch))
	{
		cout << ch;
	}
	cout << endl;
	fin.close();

	system("pause");
}

C++对二进制文件的读写操作

二进制文件不是以 ASCII 代码存放数据的,它将内存中数据存储形式不加转换地传送到
磁盘文件,因此它又称为内存数据的映像文件。因为文件中的信息不是字符数据,而是字节
中的二进制形式的信息,因此它又称为字节文件。
对二进制文件的操作也需要先打开文件,用完后要关闭文件。在打开时要用 ios::binary
指定为以二进制形式传送和存储。二进制文件除了可以作为输入文件或输出文件外,还可以
是既能输入又能输出的文件。这是和 ASCII 文件不同的地方。

用成员函数 read 和 write 读写二进制文件

对二进制文件的读写主要用 istream 类的成员函数 read 和 write 来实现。这两个成员函
数的原型为
istream& read(char *buffer,int len);
ostream& write(const char * buffer,int len);
字符指针 buffer 指向内存中一段存储空间。len 是读写的字节数。调用的方式为:
a. write(p1,50);
b. read(p2,30);
上面第一行中的 a 是输出文件流对象,write 函数将字符指针 p1 所给出的地址开始的 50 个
字节的内容不加转换地写到磁盘文件中。在第二行中,b 是输入文 件流对象,read 函数从
b 所关联的磁盘文件中,读入 30 个字节(或遇 EOF 结束),存放在字符指针 p2 所指的一段空
间内。

class Teacher
{
public:
	Teacher()
	{
		age = 33;
		strcpy(name, "");
	}
	Teacher(int _age, char *_name)
	{
		age = _age;
		strcpy(name, _name);
	}

	void print()
	{
		cout << "age: " << age << " name: " << name << endl;
	}
private:
	int age;
	char name[32];
};
//打开二进制文件
void main()
{
	char *fname = "e:2.dat";
	ofstream fout(fname, ios::binary);	//建一个输出流和文件进行关联,输出流就相当于文件了 ios::app以追加的方式打开
	if (!fout)
	{
		cout << "打开文件失败" << endl;
	}
	Teacher t1(34, "t34");
	Teacher t2(35, "t35");
	fout.write((char *)&t1, sizeof(t1));
	fout.write((char *)&t2, sizeof(t2));
	fout.close();

	//读文件
	ifstream fin(fname);	//建了一个输入流
	Teacher tmp;
	fin.read((char *)&tmp, sizeof(Teacher));
	tmp.print();
	fin.read((char *)&tmp, sizeof(Teacher));
	tmp.print();

	fin.close();
	system("pause");
}

在这里插入图片描述

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值