




版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
第9章
C++的输入和输出
9.1C++为何建立自己的输入输出系统
因为在C++中用户需要定义众多的自定义类型,但C语言的输入输出系统不支持用户自定义的类型。请看下面的类:
classmy_class{inti;floatf;char*str;}obj;对此类类型,在C语言中下面的语句是不能接受的:printf("%my_class",obj);使用C++的输入输出系统,可通过重载”<<”和”>>”运算符来解决以上问题;C++的流类比C的输入输出函数具有更大的优越性。9.2C++的流库及其基本结构9.2.1C++的流
在C++中,流类是为输入输出提供的一组类,它们都放在流库中。流总是与某一设备相联系的(例如键盘、屏幕或硬盘等),通过使用流类中定义的方法,就可以完成对这些设备的输入输出操作。
流具有方向性:与输入设备(如键盘)相联系的流称为输入流;与输出设备(如屏幕)相联系的流称为输出流;与输入输出设备(如磁盘)相联系的流称为输入输出流。
C++中包含几个预定义的流对象:标准输入流cin 与标准输入设备相关联。缺省情况下,标准输入设备是键盘。
标准输出流cout
与标准输出设备相关联,缺省情况下,标准输出设备是屏幕。非缓冲型的标准出错流cerr
与标准错误输出设备相关联。非缓冲方式,直接向显示器上输出有关信息缓冲型的标准出错流clog
与标准错误输出设备相关联。缓冲方式,clog中的信息存放在缓冲区中,缓冲区满后或遇endl时向显示器输出。9.2.2流类库
C++流类库具有两个平行的基类:streambuf类和ios类,所有其他的流类都是从它们直接或间接地派生出来的其中:ios类为输入输出操作在用户一方的接口,负责高层操作;streambuf类为输入输出操作在物理设备一方的接口,负责低层操作。
9.3预定义类型的输入输出
9.3.1无格式输入输出基于C++类库的输入输出需使用两个流对象cin和cout,还要用与之相配套的两个输入输出运算符“>>”和“<<”,其一般的格式为:
cin>>变量;
//输人
cout<<常量或变量;
//输出1.输出运算符从运算符角度来看,输出通过输出运算符“<<”来完成的。输出运算符“<<”也称插入运算符,它是一个双目运算符,有两个操作数,左操作数为ostream类的一个对象(如cout),右操作数为一个系统预定义类型的常量或变量。例如cout<<"Thisisastring.\n";完成的功能为:写字符串“Thisisastring.”到流对象cout。(cout为标准输出流,通常为屏幕。)2.输入运算符从运算符角度来看,输入操作通过输入运算符“>>”来完成。输入运算符“>>”也称提取运算符,也是一个双目运算符,有两个操作数,左面的操作数是istream类的一个对象(cin),右面的操作数是系统预定义的任何数据类型的变量。例如:intx;cin>>x;此时,用户从键盘输入的数值会自动地转换为变量x的类型,并存入变量x内。
9.3.2格式化输入输出
C++提供了两种进行格式控制的方法:一种是使用ios类中有关格式控制的成员函数进行格式控制;另一种是使用称为操纵符的特殊类型的函数进行格式控制。
1.用ios类的成员函数进行格式控制
1)状态标志字
格式控制主要是通过对状态标志字的操作来完成的。
在ios类的public部分定义了一个枚举,它的每个成员分别定义状态标志字的一个位,每一位都称为一个状态标志位。enum{skipws=0x0001,//跳过输入中的空白,可用于输出left=0x0002,//左对齐输出,可用于输出right=0x0004,//右对齐输出,可用于输出internal=0x0008,//在符号位和基指示符后填入字符,可用于输出dec=0x0010,//转换基制为十进制数,可用于输入或输出oct=0x0020,//转换基制为八进制数,可用于输入或输出hex=0x0040,//转换基制为十六进制数,可用于输入或输出showbase=0x0080,//在输出时显示基指示符,可用于输入或输出showpoint=0x0100,//在输出时显示小数点,可用于输出
uppercase=0x0200,//十六进制输出时,表示制式//和表示数值的字符一律为大写,可用于输出showpos=0x0400,//对正整数显示正号,可用于输出scientific=0x0800,//用科学表示法显示浮点数,可用于输出fixed=0x1000,//用定点形式显示浮点数,可用于输出unitbuf=0x2000,//在输出操作后立即刷新所有流,可用于输出stdio=0x4000,//在输出操作后刷新stdout和stderr,可用于输出};
这些枚举元素的值有一个共同的特点:分别使二进制表示的状态标志字的不同位为“1”,例如:skipws0x00010000000000000001left0x00020000000000000010right0x00040000000000000100
2)控制输入输出格式的成员函数
函数原型功能longios∷setf(longflags);longios∷unsetf(longflags);longios∷flags();longios∷flags(longflags);intios∷width();intios∷width(intw);intios∷precision(intp);charios∷fill();charios∷fill(charch);设置状态标志flags清除状态标志,并返回前状态标志测试状态标志设置标志flags,并返回前状态标志返回当前的宽度设置值设置域宽w,返回以前的设置设置小数位数p,返回以前的小数位数返回当前的填充字符设置填充字符ch,返回当前的填充字符例9.3成员函数进行格式控制。
cout<<"x_width="<<cout.width()<<endl;cout<<"x_fill="<<cout.fill()<<endl;cout<<"x_precision="<<cout.precision()<<endl;cout<<123<<""<<123.45678<<endl;cout<<"_________________________________\n";程序运行结果如下:x_width=0//默认为0,按实际宽度输出x_fill=//默认取空格x_precision=0//默认取0,按实际小数位数输出123123.45678-----------------------------cout<<"***x_width=10,x_fill=,x_precision=4***\n";cout.width(10);cout.precision(4);cout<<123<<""<<123.45678<<""<<234.567<<endl;cout<<"x_width="<<cout.width()<<endl;cout<<"x_fill="<<cout.fill()<<endl;cout<<"x_precision="<<cout.precision()<<endl;cout<<"_________________________________\n";程序运行结果如下:***x_width=10,x_fill=,x_precision=4***123123.4568234.567
x_width=0//所设置的域宽仅对下一个流输出操作有效,当一次输出操作完成后,域宽又恢复为0x_fill=x_precision=4-----------------------------cout<<"***x_width=10,x_fill&,x_precision=4***\n";cout.fill(‘&’);cout.width(10);cout.precision(4);cout<<123<<""<<123.45678<<endl;
cout.setf(ios::left);//默认时为右对齐cout.width(10); cout<<123<<""<<123.45678<<endl;cout<<"x_width="<<cout.width()<<endl;cout<<"x_fill="<<cout.fill()<<endl;cout<<"x_precision="<<cout.precision()<<endl;//设置了precision()和fill()后,在程序中一直有效,除非它们被重新设置程序运行结果如下:***x_width=10,x_fill=&,x_precision=4***&&&&&&&123123.4568123&&&&&&&123.4568
x_width=0x_fill=&x_precision=4
C++提供的预定义操纵符如下:(1)dec以十进制形式输入或输出整型数。
(2)hex以十六进制形式输入或输出整型数。
(3)oct以八进制形式输入或输出整型数。(4)ws用于在输入时跳过前导的空白符,可用于输入。(5)endl插入一个换行符并刷新输出流,仅用于输出。(6)ends插入一个空字符’\0’,通常用来结束一个字符串,仅用于输出(7)flush刷新一个输出流,仅用于输出2.用C++提供的预定义的操纵符进行输入输出格式控制(8)setbase(intn)设置转换基格式为为n(n的取值为0、8、10或16,缺省为0),表示采用十进制,仅用于输出。(9)resetiosflags(longf)关闭由参数f指定的格式标志,可用于输入或输出(10)setiosflags(longf)设置由参数f指定的格式标志,
可用于输入或输出(11)setfill(intch)设置ch为填充字符,缺省时为空格,可用于输入或输出(12)setprecision(intn)设置小数部分的位数,可用于输入或输出(13)setw(intn)设置域宽为n,可用于输入或输出例9.4操纵符的使用。 #include<iostream.h> #include<iomanip.h> main() {cout<<setw(10)<<123<<567<<endl;//① cout<<123<<setiosflags(ios::scientific)<<setw(20)//② <<123.456789<<endl; cout<<123<<setw(10)<<hex<<123<<endl;//③ cout<<123<<setw(10)<<oct<<123<<endl;//④ cout<<123<<setw(10)<<dec<<123<<endl;//⑤ cout<<resetiosflags(ios::scientific)<<setprecision(4)//⑥ <<123.456789<<endl; cout<<setiosflags(ios::left)<<setfill('#')<<setw(8)//⑦ <<123<<endl; cout<<resetiosflags(ios::left)<<setfill('$')<<setw(8)//⑧ <<456<<endl; return0;}
程序运行结果为:123567①1231.234567e+02②1237b③7b
173④173123⑤123.4568⑥123#####⑦$$$$$456⑧3.用户自定义的操纵符
若为输出流定义操纵符函数,则定义形式如下:
ostream&manip_name(ostream&stream){…//自定义代码returnstream;}
若为输入流定义操纵符函数,则定义形式如下:
istream&manip_name(istream&stream){…//自定义代码returnstream;}例9.5为输出流定义操纵符函数。 #include<iostream.h> #include<iomanip.h> ostream&output1(ostream&stream) {stream.setf(ios::left); stream<<setw(10)<<hex<<setfill(’&’); returnstream; } intmain() {cout<<123<<endl; cout<<output1<<123<<endl; return0; }例9.6为输入流定义操纵符函数。 #include<iostream.h> #include<iomanip.h> istream&input1(istream&in) {in>>hex; cout<<"Enternumberusinghexformat:"; returnin; } intmain() {inti; cin>>input1>>i; cout<<"***"<<hex<<i<<"***"<<dec<<i<<"***"<<endl; return0; }9.4.1重载输出运算符“<<”
定义输出运算符“<<”重载函数的一般格式如下:
ostream&operator<<(ostream&out,class_name&obj){out<<obj.item1;out<<obj.item2;...out<<obj.itemn;returnout;}
9.4用户自定义类型的输入输出9.4.2重载输入运算符“>>”
定义输入运算符函数“>>”重载函数的一般格式如下:
istream&operator>>(istream&in,class_name&obj){in>>obj.item1;in>>obj.item2;...in>>obj.itemn;returnin;}
例9.7输出运算符“<<”重载。#include<iostream.h>classcoord{intx,y;public:coord(inti=0,intj=0){x=i;y=j;}friendostream&operator<<(ostream&stream,coord&ob);};ostream&operator<<(ostream&stream,coord&ob){stream<<ob.x<<","<<ob.y<<endl;returnstream;}main(){coorda(55,66),b(100,200);cout<<a<<b;return0;}例9.8输入运算符“>>”重载。#include<iostream.h>classthree_d{public:three_d(inta,intb,intc){x=a;y=b;z=c;}friendostream&operator<<(ostream&output,three_d&ob);friendistream&operator>>(istream&itput,three_d&ob);private:intx,y,z;};ostream&operator<<(ostream&output,three_d&ob){output<<ob.x<<",";output<<ob.y<<",";output<<ob.z<<endl;returnoutput; }
istream&operator>>(istream&input,three_d&ob) { cout<<"Enterx,y,zvalue:"; input>>ob.x; input>>ob.y; input>>ob.z; returninput; } main() { three_dobj(10,20,30);//定义类three_d的对象obj cout<<obj;//输出对象obj的成员值 cin>>obj;//输入对象obj的各成员值,将原值覆盖 cout<<obj;//输出对象obj的成员值(新值) return0; }9.5文件的输入输出
9.5.1文件的打开与关闭1.文件的打开
为了对一个文件进行读写操作,应先“打开”该文件;在使用结束后,则应“关闭”文件。
在C++中,打开一个文件,就是将这个文件与一个流建立关联;关闭一个文件,就是取消这种关联。
要执行文件的输入输出,须做三件事:(1)在程序中包含头文件fstream.h;(2)建立流。建立流的过程就是定义流类的对象,例如:ifstreamin;ofstreamout;fstreamboth;分别定义了输入流对象in;输出流对象out;输入输出流对象both。
(3)使用open()函数打开文件,也就是使某一文件与上面的某一流相联系。open()函数是上述三个流类的成员函数,其原型是在fstream.h中定义的,原型为:
voidopen(constunsignedchar*filename,intmode,intaccess=filebuf::openprot);
filename:文件名,可包含路径说明。
Mode:文件打开的模式ios::in
打开文件进行读操作ios::out
打开文件进行写操作ios::ate
打开时文件指针定位到文件尾ios::app
添加模式,所有增加都在文件尾部ios::trunc如果文件已存在则清空原文件ios::nocreate
如果文件不存在则打开失败ios::binary
二进制文件(非文本文件)
对于ifstream流,mode的默认值为ios::in;对于ofstream流,mode的默认值为ios::out。Access:文件保护方式 filebuf::openprot兼容共享方式*filebuf::sh_none独占不共享filebuf::sh_read允许读共享filebuf::sh_write允许写共享
2.文件的关闭在使用完一个文件后,应该把它关闭。所谓关闭,实际上就是使打开的文件与流“脱钩”。关闭文件可使用close()函数完成,close()函数也是流类中的成员函数,它不带参数,不返回值。例如:
out.close();将关闭与流out相联接的文件。9.5.2文件的读写
1.文本文件的读写一旦文件打开了,从文件中读取文本数据与向文件中写入文本数据都十分容易,只需使用运算符“<<”与“>>”就可以了,只是必须用与文件相联接的流代替cin和cout。
例9.9把一个整数、一个浮点数和一个字符串写到磁盘文件test中。#include<fstream.h> intmain() {ofstreamfout("test"); if(!fout) {cout<<"Cannotopenoutputfile\n,"; return1; }
fout<<10<<""<<123.456<<"\"Thisisatextfile.\"\n"; fout.close(); return0;}2.二进制文件的读写
(1)用get()函数和put()函数读写二进制文件 get()函数有许多格式,其中最常用的版本原型:
istream&get(char&ch);//get()函数从相关流中只读一个字节,并把该值放入ch中并返回该流,当到达文件尾时,使该流的值为0。
其它,如istream&get(char*,intnCount,chardelim)
//函数从输入流中提取内容,直到遇到文件结束,或遇到结束符delim,或已读入nCount-1个字符.
istream&get(char*,int)put()函数的原型如下:
ostream&put(charch);put()函数将ch写入流中并返回该流。例9.11将‘a’至‘z’的26个英文字母写入文件,而后从该文件中读出并显示出来。#include<iostream.h>#include<fstream.h>voidtest_write(){ofstreamfs("d:\\test.dat");inti;charc='a';for(i=0;i<26;i++){fs.put(c);c++;}}voidtest_read(){ifstreamfs("d:\\test.dat");charc;while(fs.get(c))cout<<c;}voidmain(){test_write();test_read();}(2)用read()函数和write()函数读写二进制文件
read()和write()原型如下:
istream&read(unsignedchar*buf,intnum);ostream&write(constunsignedchar*buf,intnum);例9.12用write()函数向文件test中写入整数与双精度数。 #include<iostream.h> #inc
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
评论
0/150
提交评论