
本文共 4016 字,大约阅读时间需要 13 分钟。
本章节属于C++标准库内容
C++语言不直接处理输入输出,而是通过一族定义在标准库中的类型来处理IO。这些类型支持: 从设备读取数据、向设备写入数据的IO操作,设备可以是文件、控制台窗口。相关的IO库设施
istream(输入流)类型,提供输入操作。 ostream(输出流)类型,提供输出操作。 cin,一个istream对象,从标准输入读取数据。 cout,一个ostream对象,从标准输出写入数据。 cerr,一个ostream对象,通常用于输出程序错误消息,写入到标准错误。 运算符>>:用来从一个istream对象读取输入数据。 运算符<<:用来向一个ostream对象写入输出数据。 getline函数:从一个给定的istream中读取一行数据,存入一个给定的string对象中。1、IO类
标准库定义了其他一些IO类型。
(头文件)iostream:定义了读写流的基本类型。 (类型) istream,wistream从流读取数据。 ostream,wostream从流写入文件。 iostream,wiostream读写流。(头文件)fstream:定义了读写命名文件的类型。
(类型) ifstream,wifstream从文件中读取数据。 ofstream,wofstream向文件写入数据。 fstream,wfstream文件读写流。(头文件)sstream:定义了读写内存String对象的类型。
istringstream,wistringstream:从string读取数据。 ostringstream,wostringstream:向string写入数据。 stringstream,wstringstream:读写string。 注:为了支持使用宽字符的语言,标准库定义了一组类型和对象来操纵wchar_t类型的数据。IO类型间的关系
标准库使我们能够忽略不同类型流之间的差异,通过继承机制实现(设备类型和字符大小不会影响我们要执行的IO操作)。继承机制使我们可以声明一个特定的类继承自另一个类。我们通常可以将一个派生类对象当做基类对象来使用。【ifstream,istringstream继承自istream,那么怎么使用istream对象,对于其派生类对象也可以这么使用】(1)IO对象五拷贝或者赋值
不能对流对象赋值,不能初始化ofstream参数,不能拷贝流对象。 不能将形参或者返回类型设置为流类型。进行IO操作的函数通常以引用方式传递和返回流。读写一个IO对象会改变其状态,因此传递和返回的引用不能够是const的!!!(2)条件状态
我们访问和操纵流的条件状态。 strm::iostream: strm是一种IO类型,就是上面列出的相关类(iostream之类的)。iostate是一种机器相关的类型。提供了表达条件状态的完整功能。 对象: strm::badbit: 指出流已经崩溃。表示系统级别错误,不可恢复的读写错误。一旦置位,那么流就无法使用了。 strm::failbit: 用来指出一个IO操作失败了。发生可恢复错误。 strm::eofbit:指出流到达终点。 strm::goodbit:用来指出流未处于错误状态,此值保证为0。 方法: s.eof(): 若流s的eofbit置位。则返回true。到达文件结束位置,eofbit,failbit都会被置位。 s.fail():若流s的failbit或者badbit置位,则返回true。 s.bad():若流sbadbit置位,那么返回true。 s.good():若流处于有效状态,返回true。 使用good或者fail是确定流总体状态的正确方法 s.clear():将流s中所有条件状态复位,将流的状态设置为有效。返回void。清除所有错误标志位。 s.clear(flags):根据给定的flags标志位,将流s中对应条件状态复位。flags的类型为strm::iostate。返回void。 s.setstate(flags):根据给定的flags标志位,将流s中对应条件状态位置位。返回void。 s.rdstate():返回流s当前的状态。返回值类型为strm::iostream。注意:一个流一旦发生错误,其上后续的IO操作都会失败。只有当一个流处于无错误状态时,我们才可以从它读取数据,向它写入数据。(因此代码通常应该在使用一个流之前检查它是否处于良好状态。)
while(cin>>word){ //输入成功之后的操作}
带参数版本的clear使用方法:
用位操作将所需位复位来生成新的状态。cin.clear(cin.rdstate()&~cin.failbit&~cin.badbit);
(3)管理输出缓冲
每个输出流都管理一个缓冲区用来保存程序读写的数据。 导致缓冲刷新的原因: I.程序正常结束。作为main函数的return操作的一部分,缓冲刷新被执行。 II.缓冲区满了。使用endl来显式刷新缓冲区。 III.可以用操作符unitbuf设置流的内部状态,来清空缓冲区。一般状态下,cerr是设置成unitbuf的,因此写到cerr当中的内容都是立即被刷新的。unitbuf告诉刘在接下来的每次写操作之后都要进行一次flush操作。而nounitbuf操作符则会重置流,使其恢复使用正常的系统管理的缓冲区刷新机制。 IV.一个输出流可能被关联到另一个流当中。当读写被关联的流时,关联到的流的缓冲区会被刷新。刷新输出缓冲区
flush:刷新缓冲区,但是不输出任何额外字符。 ends:向缓冲区插入一个空字符,然后刷新缓冲区。 <如果程序异常终止,输出缓冲区是不会被刷新的。>关联输入和输出流
交互式系统通常应该关联输入流和输出流。 tie可以完成相关的任务。 无参数版本:返回指向输出流的指针。如果本对象关联到一个输出流,则返回的就是指向这个流的指针。 带参数版本(接受一个指向ostream指针)将自己关联到此ostream。 彻底解开流的关联,传递空指针。 每个流同时最多关联到一个流,但是多个流可以同时关联到同一个ostream。2、文件输入输出
关于文件相关的对象和方法:fstream ftrm;
fstream ftrm(s);
fstream ftrm(s,mode);
指定mode格式。 fstrm.open(s);
打开名为s的文件并且将文件和fstrm绑定。s可以使string类型,或者是指向C风格字符串的指针。默认的mode依赖于fstream的格式。
fstrm.close();
关闭与fstrm绑定的文件。返回void。
fstrm.is_open();
返回一个bool值,指出与fstrm关联的文件是否成功打开且尚未关闭。
(1)使用文件流对象
定义一个空文件流对象,随后调用open来将他与文件关联起来。 如果调用open失败,failbit会被置位。调用open可能会失败,所以进行open检验是一个好习惯:ifstream in(infile);ofstream out;out.open(infile+".copy");if(out){//open成功之后使用文件}
一旦文件流打开,就保持与对应文件的关联。实际上对一个已经打开的文件流调用open会失败。并且会导致failbit被置位。随后的试图使用文件流的操作都会失败。为了将文件流关联到另外一个文件,必须首先关闭已经关联的文件。一旦文件成功关闭,才可以打开新的文件。
当一个fstream对象离开作用域时,与之关联的文件会自动关闭。
当一个fstream被销毁时,close会自动调用。(2)文件模式
每个流都有吧一个关联的文件模式。用来指出如何使用文件: in:以读方式打开。 out:以写方式打开。 trunc:截断文件。 app:每次写操作前都定位到文件末尾。 ate:打开文件后立刻定位到文件末尾。 binary:以二进制方式进行IO。文件模式限制:
只可以对ofstream或者fstream对象设定out模式。 只可以对ifstream或fstream对象设定in模式。 只有当out也被设定时才可以设定trunc模式。 只要trunc没被设定,就可以设定app模式。在app模式之下,即使没有显示指定out模式,文件也是以输出方式打开。 默认情况下,即使我们没有指定trunc,以out模式打开的文件也会被截断。为了保留以out模式打开的文件的内容,我们必须同时指定app模式。 ate和binary模式可以用于任何类型的文件流对象,而且可以与其他任何文件模式组合使用。以out模式打开文件会丢弃已有数据
默认情况下,当我们打开一个ofstream的时候,文件的内容会被丢弃。阻止一个ofstream清空给定文件内容的方法是,同时指定app模式。 每次调用open的时候都会确定文件模式!!通常情况下,out模式意味着同时使用trunc模式。
3、string流
相关的对象和方法:
sstream strm;
strm未绑定的stringstream对象。
sstream strm(s);
strm是一个sstream对象,保存strings的一个拷贝。
strm.str();
返回strm所保存的string的拷贝。
strm.str(s);
将string s拷贝到strm中。返回void。
发表评论
最新留言
关于作者
