解析C語言編程對緩衝區的理解

 轉載自:http://soft.chinabyte.com/database/47/12481547.shtmlhtml

下面介紹緩衝區的知識。緩存

  1、什麼是緩衝區函數

  緩衝區又稱爲緩存,它是內存空間的一部分。也就是說,在內存空間中預留了必定的存儲空間,這些存儲空間用來緩衝輸入或輸出的數據,這部分預留的空間就叫作緩衝區。post

  緩衝區根據其對應的是輸入設備仍是輸出設備,分爲輸入緩衝區和輸出緩衝區。spa

  2、爲何要引入緩衝區htm

  咱們爲何要引入緩衝區呢?blog

  好比咱們從磁盤裏取信息,咱們先把讀出的數據放在緩衝區,計算機再直接從緩衝區中取數據,等緩衝區的數據取完後再去磁盤中讀取,這樣就能夠減小磁盤的讀寫次數,再加上計算機對緩衝區的操做大大快於對磁盤的操做,故應用緩衝區可大大提升計算機的運行速度。內存

  又好比,咱們使用打印機打印文檔,因爲打印機的打印速度相對較慢,咱們先把文檔輸出到打印機相應的緩衝區,打印機再自行逐步打印,這時咱們的CPU能夠處理別的事情。文檔

  如今您基本明白了吧,緩衝區就是一塊內存區,它用在輸入輸出設備和CPU之間,用來緩存數據。它使得低速的輸入輸出設備和高速的CPU可以協調工做,避免低速的輸入輸出設備佔用CPU,解放出CPU,使其可以高效率工做。get

  3、緩衝區的類型

  緩衝區 分爲三種類型:全緩衝、行緩衝和不帶緩衝。

  一、全緩衝

  在這種狀況下,當填滿標準I/O緩存後才進行實際I/O操做。全緩衝的典型表明是對磁盤文件的讀寫。

  二、行緩衝

  在這種狀況下,當在輸入和輸出中遇到換行符時,執行真正的I/O操做。這時,咱們輸入的字符先存放在緩衝區,等按下回車鍵換行時才進行實際的I/O操做。典型表明是鍵盤輸入數據。

  三、不帶緩衝

  也就是不進行緩衝,標準出錯狀況stderr是典型表明,這使得出錯信息能夠直接儘快地顯示出來。

  4、緩衝區的刷新

  下列狀況會引起緩衝區的刷新:

  緩衝區滿時;

  執行flush語句;

  執行endl語句;

  關閉文件。

  可見,緩衝區滿或關閉文件時都會刷新緩衝區,進行真正的I/O操做。另外,在C++中,咱們可使用flush函數來刷新緩衝區(執行I/O操做並清空緩衝區),如:

  cout<<flush; p="" cout<<endl;<="" endl控制符的做用是將光標移動到輸出設備中下一行開頭處,而且清空緩衝區。="" 將顯存的內容當即輸出到顯示器上進行顯示="">

  至關於

  cout<<」\n」 <<flush;< p="">

  5、實例演示

  一、文件操做演示全緩衝

  建立一個控制檯工程,輸入以下代碼:

  #include using namespace std; int main() { //建立文件test.txt並打開 ofstream outfile("test.txt"); //向test.txt文件中寫入4096個字符’a’ for(int n=0;n<4096;n++) { outfile<<'a'; } //暫停,按任意鍵繼續 system("PAUSE"); //繼續向test.txt文件中寫入字符’b’,也就是說,第4097個字符是’b’ outfile<<'b'; //暫停,按任意鍵繼續 system("PAUSE"); return 0; }

  上面這段代碼很容易理解,已經在代碼內部做了註釋。

  編寫這段小代碼的目的是驗證WindowsXP下全緩衝的大小是4096個字節,並驗證緩衝區滿後會刷新緩衝區,執行真正的I/O操做。

  編譯並執行,運行結果以下:

運行結果

  此時打開工程所在文件夾下的test.txt文件,您會發現該文件是空的,這說明4096個字符「a」還在緩衝區,並無真正執行I/O操做。敲一下回車鍵,窗口變爲以下:

  此時再打開test.txt文件,您就會發下該文件中已經有了4096個字符「a」。這說明全緩衝區的大小是4K(4096),緩衝區滿後執行了I/O操做,而字符「b」還在緩衝區。

  再次敲一下回車鍵,窗口變爲以下:

  此時再打開test.txt文件,您就會發現字符「b」也在其中了。這一步驗證了文件關閉時刷新了緩衝區。

  二、鍵盤操做演示行緩衝

  先介紹getchar()函數。

  函數原型:int getchar(void);

  說明:當程序調用getchar()函數時,程序就等着用戶按鍵,用戶輸入的字符被存放在鍵盤緩衝區中,直到用戶按回車爲止(回車字符也放在緩衝區中)。當用戶鍵入回車以後,getchar()函數纔開始從鍵盤緩衝區中每次讀入一個字符。也就是說,後續的getchar()函數調用不會等待用戶按鍵,而直接讀取緩衝區中的字符,直到緩衝區中的字符讀完後,才從新等待用戶按鍵。

  不知道您明白了沒有,再通俗一點講,當程序調用getchar()函數時,程序就等着用戶按鍵,並等用戶按下回車鍵返回。期間按下的字符存放在緩衝區,第一個字符做爲函數返回值。繼續調用getchar()函數,將再也不等用戶按鍵,而是返回您剛纔輸入的第2個字符;繼續調用,返回第3個字符,直到緩衝區中的字符讀完後,纔等待用戶按鍵。

  若是您尚未明白,只能怨我表達能力有限,您能夠結合如下實例體會。

  建立一個控制檯工程,輸入以下代碼:

  #include using namespace std; int main() { char c; //第一次調用getchar()函數 //程序執行時,您能夠輸入一串字符並按下回車鍵,按下回車鍵後該函數才返回 c=getchar(); //顯示getchar()函數的返回值 cout<<c<<endl; p="" }<="" 0;="" return="" system(?pause?);="" 暫停="" }="" printf(?%c?,c);="" {="" while((c="getchar())!='\n')" 直到遇到回車符才結束="" 將每次調用getchar()函數的返回值顯示出來="" 循環屢次調用getchar()函數="">

  這段小代碼也很簡單,一樣在代碼內部都有註釋。

  getchar()函數的執行就是採用了行緩衝。第一次調用getchar()函數,會讓程序使用者(用戶)輸入一行字符並直至按下回車鍵 函數才返回。此時用戶輸入的字符和回車符都存放在行緩衝區。再次調用getchar()函數,會逐步輸出行緩衝區的內容。

  好了,本人表達能力有限,仍是編譯運行程序,經過運行結果本身領會吧。

  編譯運行程序,會提示您輸入字符,您能夠交替按下一些字符,以下:

  您一直按下去,您就會發現當您按到第4094個字符時,不容許您繼續輸入字符。這說明行緩衝區的大小也是4K。

  此時您按下回車鍵,返回第一個字符’a’,以下圖:

  繼續敲一下回車鍵,將緩衝區的其它的字符所有輸出,以下圖:

  三、標準錯誤輸出不帶緩衝

  如錯誤輸出時使用:

  cerr<<」錯誤,請檢查輸入的參數!」;

  這條語句等效於:

  fprintf(stderr, 」錯誤,請檢查輸入的參數!」);

  好了,就說到這吧,祝您好運,但願能對您有所幫助

相關文章
相關標籤/搜索