[轉]c++流緩沖---rdbuf()


C++標准庫封裝了一個緩沖區類streambuf,以供輸入輸出流對象使用。每個標准C++輸出輸出流對象都包含一個指向streambuf的指針,用 戶可以通過調用rdbuf()成員函數獲得該指針,從而直接訪問底層streambuf對象。因此,可以直接對底層緩沖區進行數據讀寫,從而跳過上層的格 式化輸入輸出操作。
對於文件流類和字符串流類,分別派生了相應的流緩沖區類型,參考最后面的代碼:
流對象通過調用rdbuf()獲得了底層streambuf對象的指針,也就可以通過該指針調用streambuf支持你各種操作進行輸入輸出。本文對這些操作不予討論,在這里主要介紹如何利用該指針實現文件內容的輸出。
輸出流提供了一個重載版本operator<<,它以streambuf指針為參數,實現把streambuf對象中的所有字符輸出到輸出流 出中;輸入流也提供了一個對應的operator>>重載版本,把輸入流對象中的所有字符輸入到streambuf對象中。輸入流的get成 員重載版本中還有以streambuf指針為參數的版本,也可以用來把輸入流的東西寫入到輸出流緩沖區中。

下面用三種方法實現把一個文件的內容輸出標准輸出(當然還可以通過普通的標准格式化輸入輸出完成):
法一:通過operator<<


#include <iostream> 
#include <fstream> 
using namespace std; 
int main() 

ifstream fin("source.dat"); 
cout<<fin.rdbuf(); 
return 0; 

 

法二:利用get成員函數

 


ifstream fin("source.dat"); 
while (!fin.get(*cout.rdbuf()).eof()) { // extract a line input 
if (fin.fail()) // blank line 
fin.clear(); 
cout<<char(fin.get()); // extract '\n' 
}

 

代碼解釋:由於上面代碼中的get版本在遇到'\n'字符時,結束提取,所以需要用循環實現整個文件內容的輸出。另外,當此版本get函數遇到空行 時,因為沒有提取到任何字符(注意:get不提取回車符),注意會設置失敗標志ios::failbit,所以此時應當調用clear()函數清除錯誤標 志。同樣,因為該版本get不會提取回車符,所以需要用另一版本的get()提取回車符。

法三:利用重載的get函數

 


ifstream fin("main.cpp"); 
fin.get(*cout.rdbuf(), EOF);

 

代碼解釋:這個版本的get成員函數可以自定義提取終止符。這里通過設置為文件結束符(EOF)來達到一下提取整個文件的目的。

當然,你可以把上面的cout換成任意的輸出流,比如文件輸出流,從而可以實現文件的拷貝功能。

另外,上面代碼中並沒有使用輸入流的>>操作符,因為>>和<<是相對的,只是把操作數交換一下位置罷了。因此,你 可以把上面代碼中用out<<

 

(原文地址:http://col1.blog.163.com/blog/static/190977519201231811364675/)


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM