《C面向对象程序第13章.ppt》由会员分享,可在线阅读,更多相关《C面向对象程序第13章.ppt(55页珍藏版)》请在三一办公上搜索。
1、C+面对对象程序设计,授课老师:,第13章输入/输出流类库与文件操作,本章要点13.1 流类体系 13.2 文件操作,本章要点I/O流、流类与流类体系的概念流的输入输出控制格式文件的概念及文件的使用文件流类体系结构文本文件与二进制文件的使用,13.1.1流(stream),流(stream)是一种抽象。它负责在数据的生产者和数据的消费者之间建立联系,并负责管理数据的流动。在C+程序中,数据可从键盘流入程序中,也可以从程序流向屏幕或磁盘文件。C+的流类主要是以两个类为基础的;ios类和streambuf类,由ios类和streambuf类所派生出来的类各自负责不同的工作。ios类及其派生类用于处
2、理与输入、输出有关的操作,例如读写文件、键盘输入和屏幕输出等。,C+语言在开始使用流类时,就预定义了如下4个常用的输入输出流对象,cin:是istream类的对象,用于处理键盘输入。cout:是ostream类的对象,用于处理屏幕输出。cerr:是ostream类的对象。用于处理出错信息,并直接输出。clog:是ostream类的对象,用于处理出错信息,并使用缓冲区输出。,13.1.2输入/输出流,1.输出流cout是ostream类的对象,因为它所指向的是标准输出设备(显示器屏幕),所以它在iostream头文件中作为全局对象进行定义。cout对象定义格式如下:ostream cout(st
3、dout);cout默认指向的C+中的标准设备名,作为其构造函数的参数使用。在iostreamh头文件中,ostream类对应每个基本数据类型都有其友元函数对左移操作符进行了友元函数的重载。,2.输入流,流的输入采用提取运算符“”来实现,其左操作数为输入流类istream的对象。istream已经预定义了对C+内部数据类型的输入方法。C+中预定义了一个标准输入流对象cin,它对应于C语言中的stdin,用于从标准输入设备(通常为键盘)读入数据。下面的例子从标准输入设备读入整型数据和双精度数据,然后输出。,【例13-1】读入一个整型数据和一个双精度数据并输出,#include stdafx.h#
4、include stdio.h#include iostream.hvoid main()int i;double d;cini;cind;couti,dendl;getchar();,程序执行后输出结果如下,3 5.63,5.6提取运算表达式的值自然为输入流对象,上面例子中的两行输出语句可以连写为cid;提取运算符可以重载,由用户定义如何输入自定义的类对象。在重载提取运算符时,同时应将其重载为类的友元,而不是成员。对于任何给定的用户定义类型T,定义一个operator函数,用于从指定的输入流读取T类型的对象。,【例13-2】Point类重载插入运算符示例,#include stdafx.h#
5、include stdio.h#include iostream.hclass pointint x,y;public:point(int x,int y)point:x=x;point:y=y;point operator+(point p)return point(x+p.x,y+p.y);/接下页,point operator-(point p)return point(x-p.x,y-p.y);friend istream istream&operator(istream&in,point&pt)/接下页,char ch;inch;if(ch=c)inpt.x;inch;inpt.y;
6、inch;return in;,13.1.3流的格式控制,(1)格式控制成员函数ios类定义的格式控制成员函数必须作为流对象(如:cout、cin)的成员函数来使用,因此其调用格式为:();(2)预定义格式控制函数。C+直接提供的预定义格式控制函数为普通函数。因此其调用格式为:():,1流的输出格式控制,(1)输出宽度及填充字符。输出宽度可通过输出格式控制成员函数width(n)、填充成员函数fill(c)与预定义格式控制函数setw(n)实现。其中n为输出数据的宽度,c为填充字符。width成员函数与fill成员函数均在头文件iostreamh中说明,因此要使用这两个函数,必须在程序中包含i
7、ostreamh头文件。而预定义格式控制函数setw在头文件iomaniph中说明,要使用setw必须在程序中包含iomaniph头文件。,【例13-3】使用width成员函数控制输出宽度,#include stdafx.h#include stdio.h#include iostream.hvoid main()float a=11,22.2,33.33,44.444,55.5555;for(int i=0;i5;i+)cout.width(10);/设置输出宽度为10coutaiendl;getchar();,由于width是ios类的成员函数,所以必须作为ios类的对象cout的成员函数
8、来使用。因此,其调用格式为coutwidth(10);程序运行后输出结果:,11222333344444555555,【例13-4】将学生姓名与比赛得分通过初始化赋给数组name5、score5,使用预定义格式控制函数setw指定宽度,#include stdafx.h#include stdio.h#include iostream.h#include iomanip.hvoid main()/接下页,char*name=Zhou,Zhao,Liu,Chen,Li;double score=11,22.2,33.33,44.444,55.5555;for(int i=0;i5;i+)cout
9、setw(6)nameisetw(10)scoreiendl;getchar();程序运行后输出结果:Zhou 11Zhao 222Liu 3333Chen 44444Li 555555,说明:,由于setw不是成员函数,所以应直接调用,如:coutsetw(6);用setw(6)将字符串namei输出在宽度为6的域中,而用setw(10)将双精度数scorei输出在宽度为10的域中。setw与width都不截断数值。若数值位超过了指定宽度,则会全部显示。setw和width仅影响紧随其后的域,在一个域输出完后,域宽度将恢复其默认值。因此,setw(6)与setw(10)必须放在循环语句中,而
10、不能在循环语句前作一次性格式控制设置。,(2)输出对齐方式及其他控制,若要改变输出流的对齐方式,可使用预定义格式控制函数setiosflags来实现。预定义格式控制函数setiosflags的格式如下:setiosflags(参数)其中参数为在ios类中定义的枚举量.,2流的输入控制格式,数据的输入输出可以分为三大类:字符类、字符串类和数值类(整数、实数、双精度)。每一类又可分为多种类型,如长整型、短整型、有符号型和无符号型等。不同类型数据的输入是由类istream通过重载“”运算符来实现的。在C+中,允许用户自己定义istream的对象。但只要程序中包含头文件iostreamh,系统自动为该
11、程序产生输入流cin和输出流cout。通常用户只要利用流cin就可完成不同类型数据的输入。,【例13-5】使用预定义格式控制符dec、oct、hex及输入流对象cin输入十进制数、八进制数、十六进制数,#include#include stdafx.h#include stdio.h#include iostream.hvoid main()int a,b,c;/接下页,coutdeca;coutdecb;coutdecc;couta=decaendl;coutb=octbendl;coutc=hexcendl;getchar();,程序执行后输入:,输入一个整数(十进制数):256输入一个整
12、数(八进制数):256输入一个整数(十六进制数):256则输出:a=256b=400c=100,说明:,(1)在输入数据时,空格作为数据间的分隔符。(2)输入的数据类型必须与要提取的数据类型一致,否则会出现错误。(3)在输入数据时,回车换行符(Enter键)起两方面的作用.,13.1.4流的输入/输出成员函数,1成员函数put()成员函数put()提供一种将字符送进输出流的方法,使用形式如下:coutput(char c);或者coutput(const char c);,【例13-6】成员函数put()用法示例,#include stdafx.h#include stdio.h#includ
13、e iostream.hvoid main()char a=A,b=B;cout.put(A).put(a).put(b)endl;getchar();程序执行结果如下:AAB,2成员函数write(),成员函数write()也可提供一种将字符串送到输出流的方法,使用形式如下:coutwrite(const char*str,int n);其中,str是一个字符指针或字符数组,用来存放一个字符串;n是一个整型数,它用来表示输出显示字符串中字符的个数。若要显示整个字符串,则用strlen(str)。,【例13-7】成员函数write()用法示例,#include#includevoid Prin
14、t(char*s)cout.write(s,strlen(s);void main()char str=a string;coutThe string isstrendl;Print(str);程序执行结果如下:The string is a stringa string,13.1.5重载提取与插入运算符,为了向流插入和提取自定义类型的数据,可以对预定义的插入符和提取符的进行重载。插入符重载的一般格式如下:ostream&operator(ostream&stream,class_name&obj)重载代码return stream;,补充:,注意:第一个参数是ostream类对象的一个引用,
15、类引用名obj接收待输出的对象,返回值为ostream类对象的引用stream。提取符重载的一般格式如下:istream&operator(istream&stream,class_name&obj)重载代码return stream;注意:第一个参数是istream类对象的一个引用,stream必须是一个输入流。,13.2文件操作,在C+中有两类文件:外设文件(如键盘、显示器、打印机等)和磁盘文件,前面介绍的标准输入输出流cin、cout都是从外设文件(如键盘、显示器)输入输出数据。本节将讨论如何从磁盘文件输入输出数据,即讨论磁盘文件的建立、打开、读写和关闭操作。,13.2.1文件概述,1文
16、件文件是由文件名标识的一组有序数据的集合,文件通常存放在磁盘上。文件名是由字母数字序列组成。如:myfiletxt,youfiletxt。源程序、学生档案记录、图形、音乐等均可以作为文件存储在磁盘上。,2文件的数据格式,文件有二种数据格式,二进制文件与文本文件。(1)二进制文件:由二进制数据组成,最小存取单位为字节。(2)文本文件:由字符的ASCII码组成,最小存取单位为字符。文本文件也称为ASCII码文件。,3使用文件的方法,使用文件前必须首先打开文件,然后才能对文件进行读写操作,最后关闭文件。C+对文件的建立、打开、读写、关闭操作都是通过C+的文件流类体系来实现的。要学会C+的文件操作,必
17、须首先了解C+的文件流类体系。,13.2.2文件流类,当程序中使用文件时,要包含头文件fstreamh。1 ofstream类ofstream类由ostream类公有派生而来,它实现数据写入到文件中的各种操作。2 ifstream类ifstream类由istream类公有派生而来,它实现从文件中读数据的各种操作。3 fstream类fstream类由iostream类公有派生而来,它提供了对文件数据的读与写操作。,13.2.3文件的使用方法,1打开和关闭一个输出文件打开一个输出文件的含义是:打开一个文件,允许向这个文件中写人数据。可以通过直接创建一个ofstream类的对象来打开一个用于进行数
18、据输出的文件,如下面的语句所示:ofstream ofs(datadat);或者ofstream ofs;ofopen(datadat);,2打开和关闭一个输入文件,打开一个输入文件的含义是:打开一个文件,允许从这个文件读出数据。可以通过直接创建一个ifstream类的对象来打开一个用于进行数据读人的文件,如下面的语句所示:ifstream ifs(studentdat);或者ofstream ifs;ifs.open(studentdat);,3打开和关闭一个可同时进行输入、输出的文件,打开一个输入、输出文件的含义是:打开一个文件,允许从这个文件读出数据,也可以向这个文件写入数据。可以通过直
19、接创建一个fstream类的对象来打开一个可用于输入、输出的文件,如下面的语句所示:fstream fs(inittxt);或者fstream fs;fsopen(inittxt);,13.2.4文本文件的使用,C+文件包括文本文件和二进制文件两种类型,对它们的操作各有不同对文本文件,既可进行带格式的输入输出操作,也可进行无格式的输入输出操作,但多数情况下是前者对于二进制文件,只能进行无格式的输入输出操作。13.2.5小节讨论对二进制文件的访问操作。当只需要对数据进行顺序输入输出操作时,则适合使用文本文件。对文本文件的访问操作包括向文本文件顺序输出数据和从文本文件顺序输入数据这两个方面。所谓顺
20、序输出就是依次把数据写入到文件的末尾(当然文件结束符也随之后移,它始终占据整个文件空间的最后一个字节位置),顺序输入就是从文件开始位置起依次向后提取数据,直到碰到文件结束符为止。,open()函数的用法示例,#include stdafx.h#include stdio.h#include iostream.h#include fstream.hvoid read(ifstream T)/从文件读取数据并显示char ch;while(!T.eof()/判断是否到文件结尾T.get(ch);/读取一个字符coutch;/显示ch的值coutendl-endl;,程序接上页,void main(
21、)ifstream T;/创建ifstream类的实例TT.open(file1.txt);/利用open()函数使T与文件file1.txt建立关联read(T);/调用上面的read()函数T.close();/取消与文件file1.txt的关联coutendl;getchar();,程序运行结果,打开模式的参数表,据此,只要fileltxt存在并存储了文本内容,将看到这些内容被显示。其实文件名并不是唯一可以向open()函数或者构造函数(其实都一样)传递的参数。下面是一个函数原型:ifstream:Open(char*filename,int open_mode);应当知道filenam
22、e表示文件的名称(一个字符串),而新出现了open_mode(打开模式)。open_mode的值用来定义以怎样的方式打开文件。打开模式的参数见表,检测文件打开操作是否成功,有如下三种办法:,第一种:最通常的检测办法Xfstream File(FirstFiletxt);/X表示“I”或“O”if(!File)/判断File对象的值toutError opening the file!Abortingn;exit(1);第二种:如果文件已经被创建,返回一个错误。ofstream File(unexisting.txt,ios:nocreate);if(!File)coutError openin
23、g the file!Abortingn;exit(1);第三种:使用fail()函数。ofstream File(filer.txt,ios:nocreate);if(File.fail()coutError opening the file!Abortingn;exit(1);,13.2.5二进制文件的使用,虽然有规则格式(formatted)的文本非常有用,但有时候需要用到无格式(unformatted)的文件二进制文件。它们和可执行程序看起来一样,而与使用“”操作符创建的文件则大不相同。get()函数与put()函数则赋予读写无规则格式文件的能力,要读写一整块的数据,那么可以使用rea
24、d()和write()函数。,get()函数和put()函数应用,#include stdafx.h#include stdio.h#include iostream.h#include fstream.hvoid main()fstream File(test_file.txt,ios:out|ios:in|ios:binary);char ch;ch=o;File.put(ch);/将ch的内容写入文件File.seekg(ios:beg);/定位至文件首部File.get(ch);/读出一个字符coutchendl;/将其显示在屏幕上File.close();getchar();程序执行
25、后输出:o,read()函数和write()函数应用,#include stdafx.h#include stdio.h#include iostream.h#include fstream.h#include string.hvoid main()fstream File(test_file.txt,ios:out|ios:in|ios:binary);char arr13;strcpy(arr,Hello World!);File.write(arr,5);/将前五个字符-Hello写入文件File.seekg(ios:beg);static char read_array10;/读出些数
26、据File.read(read_array,3);/读出前三个字符coutread_arrayendl;File.close();getchar();程序执行后输出:Hel,本章小结,1.流类体系(1)流类体系。流类体系是C+中所有流类的集合,而流类是C+中为执行输入/输出操作专门定义的类,用流类定义的对象称为流,如:输入流cin,输出流cout。流是用户与设备的接口,用户通过流可以方便地进行数据的I/O操作,而不必关心数据的I/O是如何进行的。(2)流类体系的组成。流类体系由流基类ios、输入类istream、输出类ostream、输入输出类iostream等组成。由流基类ios派生出输入类
27、istream与输出类ostream,而由输入类istream与输出类ostream派生出输入输出类iostream。其派生关系可参见图13-n(3)数据文件与设备文件。数据文件存放在磁盘上,所以也称为磁盘文件,分为文本文件与二进制文件。设备文件是指输入输出设备,采用设备文件后,用户可以用使用文件方式去使用设备,其目的是方便用户。数据通常存放在磁盘文件中,当用户程序需要时,从磁盘文件中读出数据或将数据写入磁盘。为提高IO效率设置了缓冲区,缓冲区是用于暂存I/O数据的内存区。根据输入输出流是否使用缓冲区,流可分为缓冲流与非缓冲流,cin、cout、clog为缓冲流,cerr为非缓冲流。缓冲流输出
28、时仅当缓冲区满才输出。缓冲流输入时仅当换行时才从缓冲区取数。,2数据的输入输出,数据的输入/输出有两种方式,一种是用标准的输入输出流cin、cout与提取运算符“”、插入运算符“”,另一种是用输入输出成员函数get()与put()。用cin输入数据时,空格将作为数据间的分隔符。若要输入带有空格的数据必须使用成员函数get(),get函数有三种调用方式:(1)get();从输入流中提取一个字符作为函数返回值。如c=cinget();(2)get(c,n);从输入流中提取一个长度小于或等于n的字符串赋给字符串数组c。,2数据的输入输出,(3)getline(c,n);从输入流中提取一个长度小于或等
29、于n的字符行赋给字符串数组c。输出成员函数put(c)的作用是将字符c插入到输出流中去。当输出流为缓冲方式时,而缓冲区未满时,必须用flush函数才能将缓冲区数据输出到磁盘文件中。用格式控制函数可控制数据的输出格式,如控制数据输出的域宽、对齐方式、精度与进制等等。根据不同的用户,C+提供了两种格式控制函数:一种是为熟悉C+类的用户提供的格式控制成员函数(如:width),另一种是为不熟悉C+类的用户提供的预定义格式控制函数(如:setw、setiosflags、setprecision)。格式控制成员函数必须由流对象(如:cin、cout)来调用,而预定义格式控制函数可直接调用。通过重载提取运
30、算符“”与插入运算符“”,可实现对象的输入输出,如复数的输入输出等。,3文件流类体系,文件是由文件名标识的一组有序数据的集合,文件通常存放在磁盘上。文件分为文本文件与二进制文件。文件的使用过程为:打开、读写、关闭文件。文件的打开、读写、关闭必须使用文件流类定义的成员函数来完成。文件流类体系由输入文件类ifstream、输出文件类ofstream、输入输出文件类fstream等组成。文件流类中定义了用于打开、读写、关闭文什的成员函数,使用这些成员函数可实现文件的各类操作。,4文本文件的使用,文本文件的具体使用步骤如下:(1)用文件流类定义文件流对象。定义输入流对象:ifstream infile
31、;定义输出流对象:of stream outfile;定义输入/输出流对象:fstream iofile;(2)打开文件。用成员函数open()打开文件用构造函数打开打开文件的目的是使文件流对象与磁盘文件名建立联系,以便在后面的程序中使用文件流对象实现磁盘文件的读、写及关闭操作。,4文本文件的使用,(3)读写文件。文件的读写有两种方法:用提取运算符“”与插入运算符“ch)outfilech;用成员函数get()、getline()与put()对文件读与写。如:char ch,buff500;while(infileget(ch)outfileput(ch);while(infilegetlin
32、e(buff,500)outfilebuff;(4)关闭文件。用成员函数close关闭文件,如:infileclose();outfileclose();关闭文件时,系统将与该文件相关联的内存缓冲区中的数据写到文件中,收回与该文件相关的主存空间,将文件名与文件对象之间建立的关联断开。,5二进制文件的使用,二进制文件的使用与文本文件的使用类似,首先要定义文件流对象,然后用open函数打开文件,打开方式必须使用ios:binary。读写文件时要使用读函数read()与写函数write(),并可用定位函数seekg与seekp移动文件指针,随机读写文件中任一字节单元的内容。文件使用完毕后,要用close函数关闭文件。,