標籤:資料量 ring close i++ 必須 type implicit variable 大資料量
//另外由於excel資料是從資料庫裡逐步讀出然後寫入輸出資料流的所以需要將PHP的執行時間設長一點 //(預設30秒)set_time_limit(0)不對PHP執行時間做限制。 set_time_limit(0); $columns = [ ‘文章ID‘, ‘文章標題‘, ...... //‘openid‘ ]; //處理需要匯出的資料 $timeStart = strtotime(‘2018-08-08 00:00:00‘); $timeEnd = strtotime(‘2018-08-08 23:59:59‘); $arr = DB::table(‘t_wechat_user_wx4ed9e1f4e0f3eeb0‘)->select(DB::raw(‘distinct openid‘))->where(‘subscribe_time‘,‘>=‘,$timeStart)->where(‘subscribe_time‘,‘<=‘,$timeEnd); $csvFileName = ‘8月8號新增粉絲openid.xlsx‘; //設定好告訴瀏覽器要下載excel檔案的headers header(‘Content-Description: File Transfer‘); header(‘Content-Type: application/vnd.ms-excel‘); header(‘Content-Disposition: attachment; filename="‘. $csvFileName .‘"‘); header(‘Expires: 0‘); header(‘Cache-Control: must-revalidate‘); header(‘Pragma: public‘); $fp = fopen(‘php://output‘, ‘a‘);//開啟output流 mb_convert_variables(‘GBK‘, ‘UTF-8‘, $columns); fputcsv($fp, $columns);//將資料格式化為CSV格式並寫入到output流中 $accessNum = $arr->count();//從資料庫擷取總量,假設是一百萬 $perSize = 1000;//每次查詢的條數 $pages = ceil($accessNum / $perSize); $lastId = 0; for($i = 1; $i <= $pages; $i++) { //需要匯出的資料 $accessLog = $arr->offset($lastId)->limit($perSize)->get([‘openid‘])->toArray(); foreach($accessLog as $access) { $rowData = [ ......//每一行的資料 $access->openid ]; mb_convert_variables(‘GBK‘, ‘UTF-8‘, $rowData); fputcsv($fp, $rowData); $lastId ++; } unset($accessLog);//釋放變數的記憶體 //重新整理輸出緩衝到瀏覽器 ob_flush(); flush();//必須同時使用 ob_flush() 和flush() 函數來重新整理輸出緩衝。 } fclose($fp); exit();
相關即時輸出:
①通過設定實現即時輸出
ob_end_flush();//關閉緩衝
ob_implicit_flush(true);// TRUE 開啟絕對刷送 每次緩衝即時輸出 相當於每次輸出後調用flush()
header(‘X-Accel-Buffering: no‘); //關閉輸出緩衝
②通過 php 文法實現即時輸出
$buffer = ini_get(‘output_buffering‘);
echo str_repeat(‘ ‘,$buffer+1); //防止瀏覽器緩衝
ob_end_flush(); //關閉緩衝
for( $i=1; $i<=10; $i++ ){
echo ‘第 ‘.$i.‘ 次輸出.‘."<br />\n";
flush(); //重新整理緩衝(直接發送到瀏覽器)
sleep(1);
}
echo ‘輸出完畢‘;
PHP 即時產生並下載超大資料量的 Excel 檔案