C++流檔案的一些基本概念

來源:互聯網
上載者:User

一. 物件導向的標準庫
IO標準庫類型和標頭檔
標頭檔
iostream istream從流中讀取
ostream寫到流中去
iostream對流進行讀取;從istream和ostream派生而來
fstream ifstream從檔案中讀取
ofstream寫到檔案中去,由ostream派生而來
fstream讀寫檔案,由iostream派生而來
sstream istringstream從string對象讀取:由istream派生而來
ostreamstream寫到string對象中去;由ostream派生而來
stringstream對string對象進行讀寫;由iostream派生而來
IO類型在三個獨立的標頭檔中定義:iostream定義讀寫控制視窗的類型,fstream定義讀寫已命名檔案的類型,而sstream所定義的類型則用於讀寫儲存在記憶體中的string對象。
對istream&進行操作的函數,也可使用ifstream或者istringstream對象來調用。類似的,形參為ostream&類型的函數也可用ofstream或者ostringstream對象調用。因為IO通過繼承關聯,所以可以只編寫一個函數,而將他應用到三種類型的流上:控制台,磁碟檔案或者字串流。
1. 國際字元的支援
除了支援讀寫是由char類型組成的流外,標準庫還定義了一組相關的類型,支援wchar_t類型。每個類都加上w,以此與char類型的版本區分開來。於是,wostream,wistream和wiostream可以從控制視窗讀寫wchat_t類型的資料。相應的文本輸入輸出類是wifstream,wofstream和wfstream。同樣,wchar_t的讀入類型是wcin,標準輸出是wcout;而標準錯誤是wcerr。
2. IO對象不可賦值或複製
由於流對象不能複製,因此不能儲存在vector或其他容器中。另外,形參或傳回型別不能為流類型。如果需要傳遞或返回IO對象,則必須傳遞返回指向該對象的指標或引用。
一般情況下,如果需要對傳遞IO的對象進行讀寫,可用非const引用方式傳遞這個流對象。
二. 條件狀態
IO標準庫的條件狀態
strm::iostate 機器相關的類型名,由各個iostream類定義,用於條件狀態
strm::badbit strm::iostate類型的值,用於指出被破壞的流
strm::failbit strm::iostate類型的值,用於指出失敗的IO操作
strm::eofbit strm::iostate類型的值,用於指出流已經達到檔案結束符。
s.eof() 如果設定了流s的eofbit值,則該函數返回true。
s.fail() 如果設定了流s的failbit值,則返回true。
s.bad() 如果設定了流s的badbit值,則返回true。
s.good() 如果流s處於有效狀態,則該函數返回ture。
s.clear() 將s中的所有狀態值都重設為有效狀態
s.clear(flag) 將流s中的某個指定條件狀態設為有效。Flag的類型是
strm::iostate
s.setstate(flag) 給流s添加指定條件,flag的類型是strm::iostate
s.rdstate() 返迴流s的當前條件,傳回值類型為strm::iostate
流必須處於無錯誤狀態,才能用於輸入和輸出。檢查流是否可用的最簡單方法是檢查其真值:
if(cin)
//ok, 可以使用cin,它為合法值
while(cin>>word)
//ok.成功讀取操作
1. 條件狀態
所有流對象都包括一個條件狀態成員,該成員分別有setstate和clear操作管理。這個狀態成員為iostate類型。這是由各個iostream類分別定義的機器相互關聯類型。該狀態成員以二進位的形式使用。
badbit標誌著系統級的故障,如無法恢複的讀寫錯誤。如果出現了這樣的錯誤,則該流通常就不能在繼續使用了。如果出現的是可恢複錯誤,此時則設定failbit標誌,這種導致了failbit的問題是可以修正的。Eofbit實在遇到檔案結束符設定的,此時同時還設定了failbit。
流的狀態由bad,fail,eof和good動作表示。如果bad,fail或者eof任意一個為ture,則檢查流本身將顯示該流處於錯誤狀態。類似的,如果這三個條件沒有一個為true。則good操作將返回true。
2. 條件狀態的訪問
rdstate成員函數返回一個iostate類型的值,該值對應於流當前的整個條件狀態。
istream::iostate old_state=cin.rdstate();
cin.clear();
process_input():
cin.clear(old_state):
3. 多種狀態的處理
常常會出現設定或清楚多個二進位的情況。此時,可以通過多次調用setstate或者clear函數實現。另外一種方法則是安位或操作符來實現。
is.setstate(ifstream::badbit | ifstream::failbit);
三. 輸出緩衝區的管理
每個IO對象管理一個緩衝區,用於儲存程式讀寫的資料。
os<<" please enter a value: ";
系統將字串字面值儲存在與流os相關聯的緩衝區中,下面幾種情況將導致緩衝區的內容被重新整理,即寫入到真實的輸出裝置或者檔案:
a. 程式正常結束。作為main函數返回工作的一部分,將清空所有輸出緩衝區。
b. 在一些不確定到時候,緩衝區可能滿了,緩衝區在寫入下一個值之前重新整理。
c. 用操作符顯式的重新整理緩衝區,例如行分行符號endl。
d. 在每次輸出操作執行完後,用unitbuf操作符設定流的內部狀態,從而情況緩衝區。
e. 可將輸入資料流和輸出資料流關聯起來,在這種情況下,在讀輸入資料流時將重新整理其關聯的輸出緩衝區。
1. 輸出緩衝區的重新整理
除了endl操作符,C++還提供了另外的兩個類似的操縱符。第一個是經常使用的flush,用於重新整理流,但仍然不再輸出中添加任何字元。第二個是比較少用的ends,這個操作在緩衝區中插入Null 字元null,然後重新整理它。
2. unitbuf操縱符
如果需要重新整理所有輸出,最好使用unitbuf操作符。這個操作符在每次執行完寫操作後都重新整理流:
cout<< unitbuf <<"first"<<"second"<<nounitbuf;
nounitbuf操縱符將流恢複為正常的,由系統管理的緩衝區重新整理方式。
如果程式崩潰了,則不會重新整理緩衝區。如果程式不正常結束,輸出緩衝區將不會被重新整理。
3. 將輸入和輸出綁在一起
當輸入資料流和輸出資料流綁在一起時,任何讀輸入資料流的嘗試都將首先重新整理其輸出資料流相關聯的緩衝區。標準庫將count和cin綁在一起。語句:cin>>ival;導致cout關聯的緩衝區被重新整理。互動式系統通常應確保它們的輸入和輸出資料流是綁在一起的。這樣做意味著可以保證任何輸出,包括給使用者的提示,都在試圖讀之前輸出。
Tie函數可以用istream或ostream對象調用,使用一個指向ostream對象的指標形參。調用tie函數時,將實參流綁在調用該函數的對象上,如果一個流調用tie函數將其本身綁定在傳遞給tie的ostream實參對象時,則該流上的任何IO操作都會被重新整理實參所關聯的緩衝區。
四. 檔案的輸入與輸出
fstream標頭檔中定義了三種支援檔案IO的類型:
a. ifstream,由istream派生而來。
b. ofstream,由ostream派生而來
c. fstream,由iostream派生而來
fstream類型除了繼承下來的行為外,還定義了兩個自己的新操作,open和close,以及形參為要開啟的檔案名稱的建構函式。fstream,ifstream,ofstreram對象可以調用這些操作,其他的IO類型不能調用。
1. 檔案流對象的使用
有兩種方式:
a.直接用帶參數的夠造函數開啟一個檔案名稱為string類型的ifile,
ifstream infile(ifile.c_str());
b.使用預設建構函式初始化一個檔案流對象,然後調用open函數。
ifstream infile;
infile.open("in");
檢查檔案是否開啟成功,這是一個好習慣:
if(!infile)
{
cerr<<"error: unable to open input file: "<<ifile<<endl;
return -1;
}
將檔案流與新檔案重新綁定
fstream對象一旦開啟,就保持與指定檔案相關聯。如果要把fstream對象與另一個不同的檔案關聯,則必須先關閉現在的檔案,然後開啟另一個檔案。
ifstream infile("in");
infile.close();
infile.open("next");
清除檔案流的狀態
關閉流不能改變流對象的內部狀態。如果最後的讀寫操作失敗了,對象的狀態保持為錯誤模式,直到指向clear操作重新恢複流的狀態為止。調用clear後,就像重新建立了個對象一樣。如果程式員要重用檔案流讀寫多個檔案,必須在讀另一個檔案之前調用clear清除該流的狀態。
2. 檔案模式
in 開啟檔案做讀操作
out 開啟檔案做寫操作
app 在每次寫之前找到檔案尾
ate 開啟檔案後立即定位在檔案尾
trunc 開啟檔案時清空已存在的檔案流
binary 以二進位模式進行IO操作
out,trunk,和app模式只能用於指定與offstream或fstream對象關聯的檔案;in模式只能用於指定與ifstream或fstream對象相關聯的檔案。所有的檔案都可以用ate或binary模式開啟。Ate模式只有在開啟時有效:檔案開啟後將定位在檔案尾。以binary模式開啟的流則將檔案以位元組的形式處理,不解釋流中的字元。
預設時,與ifstream流對象關聯的檔案將以in模式開啟,該模式運行檔案做讀的操作,與ofstream關聯的檔案則以out模式開啟,使檔案可寫。從效果來看,為ofstream對象指定了out模式等效於同時指定了out和trunc模式。對於ofstream開啟的檔案,要儲存檔案中已存在的資料,唯一方法是顯式的指定app模式開啟。
a. 對同一檔案做輸入和輸出運算
fstream對象既可讀也可寫它所關聯的檔案。Fstream如何使用它的檔案取決於開啟檔案時指定的模式。預設情況下,fstream對象是以in和out模式同時開啟。當檔案同時以in和out開啟時不清空。如果開啟fstream所關聯的檔案時,只用out模式,而不用in模式,則檔案清空已存在的資料,如果開啟指定了trunc模式,無論是否同時指定了in模式,檔案同樣會被清空。
b. 模式是檔案的屬性而不是流屬性
只要調用open函數,就要設定檔案模式,其模式的設定可以是顯式的,也可以是隱式的。如果沒有指定檔案模式,將使用預設值。
c. 開啟模式的有效組合
out ; out | app ; out | trunc ; in ; in | out ; in | out | trunk;
五. 字串流
istringstream,由istream派生而來,提供讀string的功能
ostringstream 由ostream派生而來,提供寫string的功能
stringstream 由iostream派生而來,提供讀寫string的功能
stringstream除了繼承基類的操作外,還各自訂一個又string形參的建構函式,這個建構函式將string類型實參複製給stringstream對象。
stringstream特定的操作
stringsteam strm; 建立自由的stringstream對象
stringstream strm(s); 建立儲存s的副本的stringstream對象,其中s是string類型的對象。
strm.str(); 返回strm中儲存的string類型對象
strm.str(s); 返回string類型的s複製給strm,返回void。
1. stringstream對象的使用
將一個stringstream對象與所讀取的行綁定起來,這樣只需使用普通的string輸入操作符即可讀出每行中的單詞。
String line, word;
While ( getline(cin, line))
{
istringstream stream(line);
while( stream>>word)
//….
}
2. stringstream提供的轉換或格式化
stringstream對象的一個最常用的用法是:需要在多種資料類型之間實現自動格式化使用該類類型。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.