程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> 網頁編程 >> PHP編程 >> 關於PHP編程 >> PHP 輸出緩沖控制(Output Control) 學習

PHP 輸出緩沖控制(Output Control) 學習

編輯:關於PHP編程

PHP 輸出緩沖控制(Output Control) 學習


php 緩沖簡介       其實我對php ob 系列印象還是很模糊,具體怎麼玩的,還不是很了解,平時curd,確實對這些內容沒有深入。作為phper 甚是慚愧。網   上搜了一通,互相copy,代碼運行不能出現作者所描述現象,本文良心出品,代碼都是作者運行過。      當執行輸出的時候,比如 echo,print。輸出並沒有立即送給 web server, 而是將數據寫入 php buffer。php output_buffering 機制   好處當然提升性能。其實 php 文件最終在浏覽器上顯示,走過3個緩沖階段: php buffer=》web server buffer=》browser buffer。 最後顯   示到浏覽器     默認情況下,php buffer 是開啟的,而且該 buffer 默認值是4096,即4 kb。你可以通過在php.ini配置文件中找到output_buffering配   置。buffer是一個內存地址空間,Linux系統默認大小一般為4096(4kb),即一個內存頁。主要用於存儲速度不同步的設備或者優先級不同的設備   之間傳辦理數據的區域。通過buffer,可以使進程這間的相互等待變少。這裡說一個通俗一點的例子,你打開文本編輯器編輯一個文件的時候   ,你每輸入一個字符,操作系統並不會立即把這個字符直接寫入到磁盤,而是先寫入到buffer,當寫滿了一個buffer的時候,才會把buffer中   的數據寫入磁盤,當然當調用內核函數flush()的時候,強制要求把buffer中的髒數據寫回磁盤。     舉個例子   <?php echo "南無阿彌陀佛<br>"; header("content-type:text/html;charset='utf-8'"); echo "真善忍好!"; //output //南無阿彌陀佛 //真善忍好   header()必須在任何實際輸出之前調用,但是我們程序已經輸出了,卻正常運行。在看下面的代碼:     <?php   echo "南無阿彌陀佛<br>"; ob_flush(); header("content-type:text/html;charset='utf-8'"); echo "真善忍好!"; //output //南無阿彌陀佛 //Cannot modify header information - headers already sent by (output started at E:\php\test.php:3) //真善忍好   上面程序說明程序並沒有立即輸出,而當調用ob_flush 函數的時候才刷新緩沖,輸出。     ob_flush() 與 flush() ob_flush() , flush() 函數php 手冊上都有詳細的說明,你可以去查閱一下。二者的區別是:   ob_flush() 是刷新PHP自身的緩沖區   flush()是 它是刷新WebServer 服務器的緩沖。輸出到浏覽器。但是會出現下面的情況:   個別web服務器程序,特別是Win32下的web服務器程序,在發送結果到浏覽器之前,仍然會緩存腳本的輸出,直到程序結束為止。 有些Apache的模塊,比如mod_gzip,可能自己進行輸出緩存,這將導致flush()函數產生的結果不會立即被發送到客戶端浏覽器。 甚至浏覽器也會在顯示之前,緩存接收到的內容。例如 Netscape 浏覽器會在接受到換行或 html 標記的開頭之前緩存內容,並且在接受到    </table> 標記之前,不會顯示出整個表格。 一些版本的 Microsoft Internet Explorer 只有當接受到的256個字節以後才開始顯示該頁面,所以必須發送一些額外的空格來讓這些浏覽器   顯示頁面內容。  比如:   <?php /** Server:LightTPD/1.4.28 (Win32) X-Powered-By:PHP/5.3.27 */ echo '佛法無邊'."<BR>"; ob_flush(); flush(); sleep(1); echo '法輪常轉';   //output   上面的代碼 在 chrome 浏覽器上面 是一行一行的輸出,在ie系列的浏覽器則是全部輸出。其實就是上面的 第四條一些浏覽器只有當接收256   個字符才開始顯示。把上面的代碼改成下面形式:     <?php /** Server:LightTPD/1.4.28 (Win32) X-Powered-By:PHP/5.3.27 */ echo str_pad('',240)."\n";  echo '佛法無邊'."<BR>"; ob_flush(); flush(); sleep(1); echo '法輪常轉';   //output   這樣在ie下面就會一行一行輸出,因為超過256個字符。     ob 其他函數說明 1.ob_end_flush 與 ob_end_clean     end 的顧名思義就結束,關閉緩沖區,都是關閉輸出緩沖,一個是輸出緩沖區,一個是清除。比如     <?php /** Server:LightTPD/1.4.28 (Win32) X-Powered-By:PHP/5.3.27 */ echo 'before'; ob_end_clean(); echo str_pad('',4096)."\n"; for ($i=10; $i>0; $i--)  {      echo $i;     sleep(1); }   上述代碼是一下輸出全部內容,而不是一個一個輸出。ob_end_clean() 不是關閉了緩沖了?怎麼不是一個一個輸出呢,其實我們上面也說了,   php 不是直接輸出給浏覽器,而是 web server。 雖然php 沒有了 緩沖。但是web server 還是有的。所以下面代碼:     /** Server:LightTPD/1.4.28 (Win32) X-Powered-By:PHP/5.3.27 */ echo 'before'; ob_end_clean(); echo str_pad('',4096)."\n"; for ($i=10; $i>0; $i--)  {      flush();     echo $i;     sleep(1); }   加上flush(),就會一行一行輸出。 如果把ob_end_clean 換成 ob_end_flush  會把 before 輸出來。   其他函數 可參考手冊,比較簡單。     總結   php 腳本到浏覽器,要經過  php buffer=》web server buffer=》browser buffer。 最後顯示到浏覽器。 缺一不可。 所以我們要    ob_flush 和  flush 以及加上  echo str_pad('',4096) 才能調試出你想要的效果。

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved