




版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領
文檔簡介
第14章輸入輸出與文件輸入輸出是指程序與外部設備交換信息C++把輸入輸出看成是一個數據流輸入流:外圍設備流向內存的數據輸出流:內存流向外圍設備的數據在C++中,輸入輸出不是語言所定義的部分,而是由標準庫提供。C++的輸入輸出分為:基于控制臺的I/O基于文件的I/O基于字符串的I/O輸入輸出與文件流與標準庫輸入輸出緩沖基于控制臺的I/O基于文件的I/O基于字符串的I/O流的概念及用途
I/O操作是以對數據類型敏感的方式執行的。C++的I/O操作是以字節流的形式實現的。流實際上就是字節序列。C++提供了低級和高級I/O功能。低級I/O功能通常只在設備和內存之間傳輸一些字節。高級I/O功能把若干個字節組合成有意義的單位,如整數、浮點數、字符、字符串以及用戶自定義類型的數據。C++提供了無格式I/O和格式化I/O兩種操作。無格式I/O傳輸速度快,但使用起來較為麻煩。格式化I/O按不同的類型對數據進行處理,但需要增加額外的處理時間,不適于處理大容量的數據傳輸。流與標準庫頭文件類型iostreamistream從流中讀取ostream寫到流中去iostream對流進行讀寫,從istream和ostream派生fstreamifstream從文件中讀取,由istream派生而來ofstream寫到文件中去,由ostream派生而來fstream對流進行讀寫,由iostream派生而來sstreamistringstream從string對象中讀取,由istream派生而來ostringstream寫到string對象中去,由ostream派生而來stringstream對string對象進行讀寫,由iostream派生而來類的繼承關系iosistreamostreamifstreamofstreamiostreamfstreamistringstreamostringstreamstringstream輸入輸出與文件流與標準庫輸入輸出緩沖基于控制臺的I/O基于文件的I/O基于字符串的I/O輸入輸出緩沖C++的輸入輸出是基于緩沖實現的每個I/O對象管理一個緩沖區,用于存儲程序讀寫的數據當用戶在鍵盤上輸入數據時,鍵盤輸入的數據是存儲在輸入緩沖區中,當執行“>>”操作時,從輸入緩沖區中取數據存入變量,如緩沖區中無數據,則等待從外圍設備取數據放入緩沖區“<<”是將數據放入輸出緩沖區。如有下列語句:os<<“pleaseenterthevalue:”;系統將字符串常量存儲在與流os關聯的緩沖區中輸出緩沖區的刷新程序正常結束。作為main函數返回工作的一部分,將真正輸出緩沖區的內容,清空所有的輸出緩沖區;當緩沖區已滿時,在寫入下一個值之前,會刷新緩沖區;用標準庫的操縱符,如行結束符endl,顯式地刷新緩沖區;在每次輸出操作執行結束后,用unitbuf操縱符設置流的內部狀態,從而清空緩沖區;可將輸出流與輸入流關聯起來。在這種情況下,在讀輸入流時,將刷新其關聯的輸出緩沖區。在標準庫中,將cout和cin關聯在一起,因此每個輸入操作都將刷新cout關聯的緩沖區。輸入輸出與文件流與標準庫輸入輸出緩沖基于控制臺的I/O基于文件的I/O基于字符串的I/O基于控制臺的I/O標準的輸入輸出流對象cin是類istream的對象,它與標準輸入設備(通常指鍵盤)連在一起。cout是類ostream的對象,它與標準輸出設備(通常指顯示設備)連在一起。cerr是類osteam的對象,它與標準錯誤輸出設備連在一起。
clog是類ostream的對象,它與標準錯誤輸出設備連在一起。基于控制臺的I/O輸出流輸入流格式化輸入/輸出輸出流C++的類ostream提供了格式化輸出和無格式輸出的功能輸出功能包括用流插入運算符輸出標準類型的數據;用成員函數put輸出字符;成員函數write的無格式化輸出;輸出特定形式數值輸出標準類型的數據標準類型的數據用流插入運算符<<輸出格式:cout<<數據項;C++能自動判別數據類型,并根據數據類型解釋內存單元的信息,把它轉換成字符顯示在顯示器上。
輸出流#include<iostream>usingnamespacestd;intmain(){inta=5,*p=&a;doublex=1234.56;charch='a';cout<<"a="<<a<<endl;cout<<"x="<<x<<endl;cout<<"ch="<<ch<<endl;
cout<<"*p="<<*p<<endl;cout<<"p="<<p<<endl;
return0;}a=5x=1234.56ch=a*p=5p=0012FF7C地址用十六進制輸出指針輸出的特例如果輸出的指針變量是一個指向字符的指針時,C++并不輸出該指針中保存的地址,而是輸出該指針指向的字符串。如果確實想輸出這個指向字符的指針變量中保存的地址值,可以用強制類型轉換,將它轉換成void*類型#include<iostream>usingnamespacestd;intmain(){char*ptr="abcdef";cout<<"ptr指向的內容為:"<<ptr<<endl;cout<<"ptr中保存的地址為:"<<(void*)ptr<<endl;
return0;}ptr指向的內容為:abcdefptr中保存的地址為:0046C04C用成員函數put輸出字符cout.put(‘A’);
將字符A顯示在屏幕上,并返回當前對象。
連續調用put函數:
cout.put(‘A’).put(‘\n’);
該語句在輸出字符A后輸出一個換行符。圓點運算符(.)從左向右結合。cout.put(65);用ASCII碼值表達式調用put函數,語句也輸出字符A。write的無格式輸出
調用成員函數write可實現無格式輸出。它有兩個參數。第一個參數是一個指向字符的指針,第二個參數是一個整型值。這個函數把一定量的字節從字符數組中輸出。這些字節都是未經任何格式化的,僅僅是以原始數據形式輸出。
例如:
charbuffer[]
=“HAPPYBIRTHDAY”;
cout.write(buffer,10
);
輸出buffer的10個字節函數調用:
cout.write(“ABCDEFGHIJKLMNOPQRSTUVWXYZ”,10);
顯示了字母表中的前10個字母。
基于控制臺的I/O輸出流輸入流格式化輸入/輸出輸入流流讀取運算符>>Get函數Getline函數其他函數流讀取運算符>>輸入流最常用的操作是流讀取運算符。流讀取運算符通常會跳過輸入流中的空格、tab鍵、換行符等空白字符。當遇到輸入流中的文件結束符時,流讀取運算符返回0(false);否則,流讀取運算符返回對調用該運算符的對象的引用。流讀取運算符在讀入EOF時返回0的特性使得它經常被用作為循環的判別條件,以避免選擇特定的表示輸入結束的值EOF在各個系統中有不同的表示。在windows中是Ctri+z實例統計某次考試的最高成績。假定事先不知道有多少個考試成績,在輸入結束時用戶會輸入表示成績輸入完畢的文件結束符。當用戶輸入文件結束符時,while循環結構中的條件(cin>>grade)將變為0(即false)。#include<iostream>usingnamespacestd;intmain(){intgrade,highestGrade=-1;cout<<"Entergrade(enterend-of-filetoend):";while(cin>>grade){if(grade>highestGrade)highestGrade=grade;cout<<"Entergrade(enterend-of-filetoend):";}cout<<"\n\nHighestgradeis:"<<highestGrade<<endl;return0;}
輸出結果:
Entergrade(enterend-of-filetoend):67
Entergrade(enterend-of-filetoend):87
Entergrade(enterendoffiletoend):73
Entergrade(enterend-of-filetoend):95
Entergrade(enterend-of-filetoend):34
Entergrade(enterend-of-filetoend):99
Entergrade(enterend-of-filetoend):
^z
Heighestgradeis:99成員函數getGet函數用于讀入字符或字符串get函數有三種格式:不帶參數帶一個參數帶三個參數不帶參數的get函數不帶參數的get函數從當前對象讀入一個字符,包括空白字符以及表示文件結束的EOF,并將讀入值作為函數的返回值返回。如下列語句while((ch=cin.get())!=EOF)cout<<ch;將輸入的字符回顯在顯示器上,直到輸入EOF。#include<iostream>Usingnamespacestd;
intmain()
{charc;
while((c=cin.get())!=EOF)
cout.put(c);
cout<<"\nEOFinthissystemis:"<<c;
return0;
}輸出結果:
Enterasentencefollowedbyend-of-file:
Testingthegetandputmemberfunctions^z
Testingthegetandputmemberfunctions
EOFinthissystemis:-1
帶一個參數的get函數例如,下面的循環語句將輸入一個字符串,存入字符數組ch,直到輸入回車。cin.get(ch[0]);for(i=0;ch[i]!='\n';++i)cin.get(ch[i+1]);ch[i]='\0';帶一個字符類型的引用參數,它將輸入流中的下一字符(包括空白字符)存儲在參數中,它的返回值是當前對象的引用。帶有三個參數的get成員函數參數分別是接收字符的字符數組、字符數組的大小和分隔符(默認值為‘\n’)。函數或者在讀取比指定的最大字符數少一個字符后結束,或者在遇到分隔符時結束。為使字符數組(被程序用作緩沖區)中的輸入字符串能夠結束,空字符會被插入到字符數組中。函數不把分隔符放到字符數組中,但是分隔符仍然會保留在輸入流中。要輸入一行字符,可用下列語句:cin.get(ch,80,’\n’);或cin.get(ch,80);要輸入一個以句號結尾的句子,可用下面的語句:cin.get(ch,80,’.’);當遇到輸入結束符時,程序插入一個’\0’作為輸入字符串的結束標記,輸入結束符沒有放在字符數組中,而是保留在輸入流中,下一個和輸入相關的語句會讀入這個輸入結束符。如對應于語句cin.get(ch,80,’.’);用戶輸入abcdef.↙則ch中保存的是字符串“abcdef”,而“.”仍保留在輸入緩沖區中。如果繼續調用cin.get(ch1);或cin>>ch1
;則字符變量ch1中保存的是“.”。#include<iostream>Usingnamespacestd;
intmain()
{
constintSIZE=80;
charbuffer1[SIZE],buffer2[SIZE];
cout<<"Enterasentence:\n";
cin>>buffer1;
cout<<"\nThestringreadwithcinwas:\n"
<<buffer1<<"n\n";
cin.get(buffer2,SIZE);
cout<<"Thestringreadwithcin.getwas:\n"
<<buffer2<<endl;
return0;
}輸出結果:
Enterasentence:
Contrastingstringinputwithcinandcin.get
Thestringreadwithcinwas:
Contrasting
Thestringreadwithcin.getwas:
stringinputwithcinandcin.get
成員函數getline與帶三個參數的get函數類似,它讀取一行信息到字符數組中,然后插入一個空字符。所不同的是,getline要去除輸入流中的分隔符(即讀取字符并刪除它),但是不把它存放在字符數組中。#include<iostream>Usingnamespacestd;
intmain()
{constSIZE=80;
charbuffe[SIZE];
cout<<"Enterasentence:\n";
cin.getline(buffer,SIZE);
cout<<"\nThesentenceenteredis:\n"<<buffer<<endl;
return0;
}輸出結果:
Enterasentence:
Usingthegetlinememberfunction
Thesentenceenteredis:
Usingthegetlinememberfunction
用Read函數輸入調用成員函數read可實現無格式輸入。它有兩個參數。第一個參數是一個指向字符的指針,第二個參數是一個整型值。這個函數把一定量的字節從輸入緩沖區讀入字符數組,不管這些字節包含的是什么內容。
例如:
charbuffer[80];
cin.read(buffer,10
);
讀入10個字節,放入buffer如果還沒有讀到指定的字符數,遇到了EOF,則讀操作結束。此時可以用成員函數gcount統計輸入的字符個數#include<iostream>usingnamespacestd;intmain(){charbuffer[80];cout<<"Enterasentence:\n";cin.read(buffer,20);cout<<"\nThesentenceenteredwas:\n";cout.write(buffer,cin.gcount());cout<<endl;cout<<"一共輸入了"<<cin.gcount()<<"個字符\n";return0;}
輸出結果:
Enterasentence:
Usingtheread,write,andgcountmemberfunctions
Thesentenceenteredwas:
Usingtheread,write一共輸入了20個字符基于控制臺的I/O輸出流輸入流格式化輸入/輸出格式化輸入/輸出C++提供了大量的用于執行格式化輸入/輸出的流操縱算子和成員函數。功能:整數流的基數:dec、oct、hex和setbase設置浮點數精度:precision、setprecision設置域寬:setw、width設置域填充字符:fill、setfill設置整型數的基數輸入輸出流中的整型數默認為十進制表示。為了使流中的整型數不局限于十進制,可以插入hex操縱符將基數設為十六進制,插入oct操縱符將基數設為八進制,也可以插入dec操縱符將基數重新設為十進制也可以通過流操縱符setbase來改變流的基數。該操縱符有一個整型參數,它的值可以是16,10或8,表示將整型數的基數設為十六進制,十進制或八進制使用任何帶參數的流操縱符,都必須包含頭文件iomanip流的基數值只有被顯式更改時才會變化,否則一直沿用原有的基數。hex、oct、dec和setbase#include<iostream>#include<iomanip>usingnamespacestd;intmain(){intn;cout<<"Enteraoctalnumber:";cin>>oct>>n;cout<<"octal"<<oct<<n<<"inhexdecimalis:"<<hex<<n<<'\n';
cout<<"hexdecimal"<<n<<"indecimalis:"<<dec<<n<<'\n';cout<<setbase(8)<<"octal"<<n<<"inoctalis:"<<n<<endl;return0;}Enteraoctalnumber:30Octal30inhexdecimalis:18Hexdecimal18indecimalis:24Octal30inoctalis:30設置浮點數精度設置浮點數的精度(即,實型數的有效位數)可以用流操縱符setprecision或基類ios的成員函數precision來實現。一旦調用了這兩者之中的某一個,將影響所有輸出的浮點數的精度,直到下一個設置精度的操作為止。這個操縱符和成員函數都有一個參數,表示有效位數的長度。#include<iostream>#include<iomanip>usingnamespacestd;intmain(){doublex=123.456789,y=9876.54321;
for(inti=9;i>0;--i){cout.precision(i);cout<<x<<'\t'<<y<<endl;}//或寫成for(inti=9;i>0;--i)//cout<<setprecision(i)<<x<<'\t'<<y<<endl;
return0;}執行結果123.4567899876.54321123.456799876.5432123.45689876.543123.4579876.54123.469876.5123.598771239.88e+0031.2e+0029.9e+0031e+0021e+004設置域寬域寬是指數據所占的字符個數。設置域寬可以用基類的成員函數width,也可以用流操縱符(setw)。width和setw都包含一個整型的參數,表示域寬。設置域寬可用于輸入,也可用于輸出。設置寬度是適合于下一次輸入或輸出,之后的操作的寬度將被設置為默認值。當沒有設置輸出寬度時,C++按實際長度輸出。如整型變量a=123,b=456,則輸出cout<<a<<b;將輸出123456。一旦設置了域寬,該輸出必須占滿域寬。如果輸出值的寬度比域寬小,則插入填充字符填充。默認的填充字符是空格。如果實際寬度大于指定的域寬,則按實際寬度輸出。如語句cout<<setw(5)<<x<<setw(5)<<y<<endl;的輸出為123456每個數值占5個位置,前面用空格填充。設置域寬也可用于輸入。當輸入是字符串時,如果輸入的字符個數大于設置的域寬時,C++只讀入域寬指定的字符個數。如有定義chara[9],b[9];執行語句cin>>setw(5)>>a>>setw(5)>>b;用戶在鍵盤上的響應為abcdefghijklm則字符串a的值為“abcd”,字符串b的值為“defg”。其他流操縱符流操縱符描述skipws跳過輸入流中的空白字符,使用流操縱符noskipws復位該選項left輸出左對齊,必要時在右邊填充字符right輸出右對齊,必要時在左邊填充字符showbase指名在數字的前面輸出基數,以0開頭表示八進制,0x或0X表示十六進制。使用流操縱符noshowbase復位該選擇uppercase指明當顯示十六進制數時使用大寫字母,并且在科學計數法輸出時使用大寫字母E。可以用流操縱符nouppercase復位showpos在正數前顯示加號(+),可以用流操縱符noshowpos復位scientic以科學計數法輸出浮點數fixed以定點小數形式輸出浮點數setfill設置填充字符,它有一個字符型的參數用戶自定義的流操縱算子程序員可以定義自己的流操縱符例如,定義輸出流操縱符格式如下:ostream&操縱符名(ostream&os){需要執行的操作}#include<iostream>usingnamespacestd;ostream&tab(ostream&os){returnos<<'\t';}intmain(){inta=5,b=7;cout<<a<<tab<<b<<endl;return0;}57輸入輸出與文件流與標準庫輸入輸出緩沖基于控制臺的I/O基于文件的I/O基于字符串的I/O基于文件的I/O文件的概念文件和流文件的順序訪問文件的隨機訪問訪問有記錄概念的文件文件的概念文件是駐留在外存儲器上、具有標識名的一組信息集合,用來永久保存數據。與文件相關的概念有:數據項(字段)記錄文件數據庫如在一個圖書管理系統中,有一個數據庫。這個數據庫由書目文件、讀者文件及其它輔助文件組成。書目文件中保存的是圖書館中的所有書目信息,每本書的信息構成一條記錄。每本書需要保存的信息有:書名、作者、出版年月、分類號、ISBN號、圖書館的館藏號以及一些流通信息。其中書名是一個字段,作者也是一個字段。基于文件的I/O文件的概念文件和流文件的順序訪問文件的隨機訪問訪問有記錄概念的文件文件和流C++語言把每一個文件都看成一個有序的字節流(把文件看成n個字節)每一個文件以文件結束符(end-of-filemarker)結束當打開一個文件時,該文件就和某個流關聯起來與這些對象相關聯的流提供程序與特定文件或設備之間的通信通道例如.cin對象(標準輸入流對象)使程序能從鍵盤輸入數據,cout對象(標準輸出流對象)使程序能向屏幕輸出數據。文件訪問過程定義一個流對象打開文件:將流對象與文件關聯起來訪問文件關閉文件:切斷流對象與文件的關聯定義一個流對象C++有三個文件流類型:ifstream:輸入文件流ofstream:輸出文件流fstream:輸入輸出文件流如:ifstreaminfile;打開文件用流對象的成員函數open打開文件用流對象的構造函數打開文件無論是成員函數open還是通過構造函數,都有兩個參數:打開的文件名文件打開模式如果文件打開失敗,返回0文件打開模式文件打開模式名含義in打開文件,做讀操作out打開文件,做寫操作app在每次寫操作前,找到文件尾ate打開文件后,立即將文件定位在文件尾trunc打開文件時,清空文件binary以二進制模式進行輸入輸出操作默認打開方式ifstream流對象是以in模式打開ofstream流關聯的文件則以out模式打開ofstream對象以in和out方式打開文件打開打開輸入文件:ifstreaminfile;infile.open(“file1”);或infile.open(“file1”,ifstream::in);也可以利用構造函數直接打開:ifstreaminfile(“file1”);或ifstreaminfile(“file1”,ifstream::in);打開輸出文件ofstreamoutfile;outfile.open(“file2”);或outfile.open(“file2”,ofstream::out);也可以利用構造函數直接打開:ofstreamoutfile(“file2”);或ofstreamoutfile(“file2”,ofstream::out);打開輸入輸出文件fstreamiofile(“file3”);fstreamiofile(“file3”,fstream::in|fstream::out);文件關閉用成員函數closemain函數執行結束時,會關閉所有打開的文件良好的程序設計習慣:文件訪問結束時,關閉文件基于文件的I/O文件的概念文件和流文件的順序訪問文件的隨機訪問訪問有記錄概念的文件文件的順序訪問C++文件的讀寫和控制臺讀寫一樣,可以用流提取運算符“>>”從文件讀數據,也可以用流插入運算符”<<”將數據寫入文件,也可以用文件流的其他成員函數讀寫文件,如get函數,put函數等。在讀文件操作中,經常需要判斷文件是否結束(文件中的數據是否被讀完)。這可以通過基類ios的成員函數eof來實現。eof函數不需要參數,返回一個整型值。當讀操作遇到文件結束時,該函數返回1,否則返回0。另一種判斷讀結束的方法是用流提取操作的返回值。當“>>”操作成功時,返回true。文件訪問實例將數字1到10寫入文件file,然后從file中讀取這些數據,把它們顯示在屏幕上。首先用輸出方式打開文件file。如文件file不存在,則自動創建一個,否則打開磁盤上的文件,并清空。用一個循環依次將1到10用流插入符插入文件,并關閉文件。然后,再用輸入方式打開文件file,讀出所有數據,并輸出到屏幕上。#include<iostream>#include<fstream>usingnamespacestd;intmain(){ofstreamout("file");ifstreamin;inti;if(!out){cerr<<"createfileerror\n";return1;}for(i=1;i<=10;++i)out<<i<<'';out.close();in.open("file");if(!in){cerr<<"openfileerror\n";return1;}while(in>>i)cout<<i<<'';
in.close();return0;}執行結果執行該程序后,文件file中的內容為12345678910該程序的輸出結果是12345678910包含各種類型數據的文件操作#include<fstream>#include<iostream>usingnamespacestd;intmain(){ofstreamfout("test");if(!fout){cerr<<"cannotopenoutputfile\n";return1;}fout<<10<<""<<123.456<<"\"Thisisatextfile\"\n";
fout.close();return0;}執行結果文件中的內容為10123.456"Thisisatextfile"讀文件#include<fstream>#include<iostream>usingnamespacestd;intmain(){ifstreamfin("test");chars[80];inti;floatx;if(!fin){cout<<"cannotopeninputfile\n";return1;}fin>>i>>x>>s;cout<<i<<""<<x<<s;fin.close();
return0;}10123.456"Thisfin>>i>>x;fin.getline(s,80,‘\n’);基于文件的I/O文件的概念文件和流文件的順序訪問文件的隨機訪問訪問有記錄概念的文件文件定位指針文件定位指針:是一個long類型的數據,指出當前讀寫的位置C++文件有兩個定位指針:讀指針和寫指針當文件以輸入方式打開時,讀指針指向文件中的第一個字節。文件以輸出方式打開時,寫指針指向文件中的第一個字節。當文件以添加方式打開時,寫指針指向文件尾。文件的隨機訪問指定文件定位指針的值,從任意指定位置開始讀寫獲取文件定位指針的當前位置:成員函數tellg和tellp設置文件定位指針的位置:成員函數seekg和seekp成員函數seekg和seekpseekg和seekp都有兩個參數:第一個參數通常為long類型的整數,表示偏移量;第二個參數指定移動的起始位置尋找方向:ios::beg(默認):相對于流的開頭ios::cur:相對于流當前位置ios::end:相對于流結尾文件位置指針的例子
//positiontothenthbyteoffileObject
//assumesios::beg
fileObject.seekg(n);
//positionnbytesforwardinfileObject
fileObject.seekg(n,ios::cur);
//positionybytesbackfromendoffileObject
fileObject.seekg(y,ios::end);
//positionatendoffileObject
fileObject.seekg(0,ios::end);隨機讀寫實例#include<iostream>#include<fstream>usingnamespacestd;intmain(){fstreamin("file");inti;
if(!in){cerr<<"openfileerror\n";return1;}in.seekp(10);in<<20;in.seekg(0);while(in>>i)cout<<i<<'';in.close();return0;}執行后:123452078910執行前:12345678910基于文件的I/O文件的概念文件和流文件的順序訪問文件的隨機訪問訪問有記錄概念的文件訪問要求立即訪問到文件甚至大型文件中指定的記錄可以在不破壞其他數據的情況下把數據插入到隨機訪問文件中。也能在不重寫整個文件的情況下更新和刪除以前存儲的數據。實現考慮要求記錄長度是固定的。可以使用istream中的read函數和ostream中的write函數能夠做到。如number是整型變量寫入:outFile.write(reinterpret_cast<constchar*>(&number)),sizeof(number));讀出:inFile.read(reinterpret_cast<char*>(&number)),sizeof(number));實例:圖書館的書目管理系統如果每本書需要記錄的信息有:館藏號(整型數):要求自動生成書名(最長20個字符的字符串)借書標記。借書標記中記錄的是借書者的借書證號,假設也是整型數。該系統需要實現的功能有:初始化系統添加書借書還書顯示書庫信息文件設計設計一個文件book,該文件中的每個記錄保存一本書的信息。文件中的記錄可按館藏號的次序存放,這樣可方便實現添加書和借還書的功能。添加書時,只要將這本書對應的記錄添加到文件尾。借還書時,可以根據館藏號計算記錄的存儲位置,修改相應的記錄。book類設計數據成員:館藏號、書名、借書標記為了提供館藏號自動生成,需要保存系統中最大的館藏號。這個值可以作為書目類的靜態成員。成員函數:構造函數借書還書顯示書的詳細信息靜態成員初始化靜態成員值加1
Book.h#ifndef_book_h#define_book_h#include<cstring>#include<iostream>#include<iomanip>#include<fstream>usingnamespacestd;classbook{ intno; charname[20]; intborrowed; staticintno_total;public:book(constchar*s=""){no=no_total;borrowed=0;strcpy(name,s);}voidborrow(intreaderNo)//借書{if(borrowed!=0)cerr<<"本書已被借,不能重復借\n";elseborrowed=readerNo;}voidReturn(){//還書if(borrowed==0)cerr<<"本書沒有被借,不能還\n";elseborrowed=0; }
voiddisplay()//顯示書的信息{cout<<setw(10)<<no<<setw(20)<<name<<setw(10)<<borrowed<<endl;}staticvoidresetTotal(){no_total=0;}//最大館藏號復位staticvoidaddTotal(){++no_total;}//館藏號加1};intbook::no_total=0;//靜態數據成員的定義#endif系統分解系統可分解成五大功能,每個功能用一個函數實現。Main函數顯示菜單,根據用戶的選擇調用相應的函數Main函數#include"book.h"voidinitialize();//系統初始化voidaddBook();//添加新書voidborrowBook();//借書voidreturnBook();//還書voiddisplayBook();//顯示所有的書目信息intmain(){intselector;while(true){ cout<<"0--退出\n"; cout<<"1--初始化文件\n"; cout<<"2--添加書\n"; cout<<"3--借書\n"; cout<<"4--還書\n"; cout<<"5--顯示所有書目信息\n"; cout<<"請選擇(0-5):";cin>>selector; if(selector==0)break; switch(selector) {case1:initialize();break; case2:addBook();break; case3:borrowBook();break; case4:returnBook();break; case5:displayBook();break; } }return0;}Initialize的實現voidinitialize(){ ofstreamoutfile("book");
book::resetTotal(); outfile.close();}addBook的實現voidaddBook(){ charch[20]; book*bp; ofstreamoutfile("book",ofstream::app); book::addTotal(); cout<<"請輸入書名:";cin>>ch;bp=newbook(ch);outfile.write(reinterpret_cast<constchar*>(bp),sizeof(*bp));
deletebp; outfile.close();}borrowBookvoidborrowBook(){intboo
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯系上傳者。文件的所有權益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
- 4. 未經權益所有人同意不得將文件中的內容挪作商業或盈利用途。
- 5. 人人文庫網僅提供信息存儲空間,僅對用戶上傳內容的表現方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
- 6. 下載文件中如有侵權或不適當內容,請與我們聯系,我們立即糾正。
- 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 防汛應急搶險培訓
- 天津仁愛學院《古代文學4》2023-2024學年第一學期期末試卷
- 2025建筑工程公司目標成本預算承包合同
- 景德鎮藝術職業大學《多文體閱讀(二)》2023-2024學年第二學期期末試卷
- 2025的企業勞動合同
- 2025商場宣傳承包合同示范文本
- 濟南護理職業學院《園林植物栽培學實踐(二)》2023-2024學年第二學期期末試卷
- 南水北調大工程施工方案
- 逆做擋墻施工方案
- 2025年茶葉包裝設計作品版權轉讓合同書
- 保潔管理目視化服務標準手冊
- 《無人機攝影測量》考試復習題庫(含答案)
- 工程全過程造價咨詢服務方案(技術方案)
- 項目服務保障措施
- 三級安全教育登記卡(新)
- 【建筑屋面滲漏問題及解決對策研究8000字(論文)】
- 自身免疫性腦炎診治護理查房
- BIM技術在招投標中的綜合應用
- 藥學專業副主任藥師試題
- 泉州開元寺博物館建筑中妙音鳥的翅前之功
- 嬰幼兒體格測量身高(身長)的測量課件
評論
0/150
提交評論