您好,登錄后才能下訂單哦!
小編給大家分享一下redis管道pipeline怎么用,相信大部分人都還不怎么了解,因此分享這篇文章給大家參考一下,希望大家閱讀完這篇文章后大有收獲,下面讓我們一起去了解一下吧!
Redis使用的是客戶端-服務(wù)器(CS)模型和請求/響應(yīng)協(xié)議的TCP服務(wù)器。這意味著通常情況下一個請求會遵循以下步驟:
客戶端向服務(wù)端發(fā)送一個查詢請求,并監(jiān)聽Socket返回,通常是以阻塞模式,等待服務(wù)端響應(yīng)。
服務(wù)端處理命令,并將結(jié)果返回給客戶端。
分析
普通模式:由于通信會有網(wǎng)絡(luò)延遲,假如client和server之間的包傳輸時間需要0.125秒。那么上面的三個命令6個報文至少需要0.75秒才能完成。這樣即使redis每秒能處理100個命令,而我們的client也只能一秒鐘發(fā)出四個命令。這顯然沒有充分利用 redis的處理能力。
管道模式:(pipeline)可以一次性發(fā)送多條命令并在執(zhí)行完后一次性將結(jié)果返回,pipeline通過減少客戶端與redis的通信次數(shù)來實現(xiàn)降低往返延時時間,而且Pipeline 實現(xiàn)的原理是隊列,而隊列的原理是時先進(jìn)先出,這樣就保證數(shù)據(jù)的順序性。 Pipeline 的默認(rèn)的同步的個數(shù)為53個,也就是說arges中累加到53條數(shù)據(jù)時會把數(shù)據(jù)提交。其過程如下圖所示:client可以將三個命令放到一個tcp報文一起發(fā)送,server則可以將三條命令的處理結(jié)果放到一個tcp報文返回。
??需要注意到是用 pipeline方式打包命令發(fā)送,redis必須在處理完所有命令前先緩存起所有命令的處理結(jié)果。打包的命令越多,緩存消耗內(nèi)存也越多。所以并不是打包的命令越多越好。具體多少合適需要根據(jù)具體情況測試。
??
//產(chǎn)生100萬條數(shù)據(jù)到指定文件 declare(strict_types=1);//開啟強類型模式 function random($length, $numeric = false) { $seed = base_convert(md5(microtime() . $_SERVER['DOCUMENT_ROOT']), 16, $numeric ? 10 : 35); $seed = $numeric ? (str_replace('0', '', $seed) . '012340567890') : ($seed . 'zZ' . strtoupper($seed)); if ($numeric) { $hash = ''; } else { $hash = chr(rand(1, 26) + rand(0, 1) * 32 + 64); $length--; } $max = strlen($seed) - 1; for ($i = 0; $i < $length; $i++) { $hash .= $seed{mt_rand(0, $max)}; } return $hash; } $filePath = './data.txt'; for ($i = 0; $i <= 1000000; $i++) { $str = random(10, true); file_put_contents($filePath, $str . PHP_EOL, FILE_APPEND); }
//讀取數(shù)據(jù)通過管道方式寫入到redis $lines = file_get_contents($filePath);//獲取文件內(nèi)容 ini_set('memory_limit', '-1');//不要限制Mem大小,否則會報錯 $arr = explode(PHP_EOL, $lines);//轉(zhuǎn)換成數(shù)組 //echo $arr['1000000'] ?? 'null'; try { $redis = new \Redis(); $redis->connect('192.168.1.9', 6379); $redis->auth('*****');//密碼驗證 $redis->select(0);//選擇庫 $redis->pipeline();//開啟管道 foreach ($arr as $key => $value) { $redis->hsetNx('helloworld', (string)$key, $value); } $redis->exec(); echo $redis->hGet('helloworld', '1000000') . PHP_EOL; echo $redis->hGet('helloworld', '1000001') . PHP_EOL; } catch (\Exception $e) { echo $e->getMessage(); }
//批量設(shè)置 try { $redis = new \Redis(); $redis->connect('192.168.1.9', 6379); $redis->auth('******'); $redis->select(0); $redis->pipeline();//開啟管道 $redis->set('str1', 'h'); $redis->set('str2', 'e'); $redis->set('str3', 'l'); $redis->set('str4', 'l'); $redis->set('str5', 'o'); $redis->set('str6', 'w'); $redis->set('str7', 'o'); $redis->set('str8', 'r'); $redis->set('str9', 'l'); $redis->set('str10', 'd'); $result = $redis->exec(); print_r($result); } catch (\Exception $e) { echo $e->getMessage(); } 結(jié)果: Array ( [0] => 1 [1] => 1 [2] => 1 [3] => 1 [4] => 1 [5] => 1 [6] => 1 [7] => 1 [8] => 1 [9] => 1 )
//批量讀取 try { $redis = new \Redis(); $redis->connect('192.168.1.9', 6379); $redis->auth('******'); $redis->select(0); $redis->pipeline();//開啟管道 $redis->get('str1'); $redis->get('str2'); $redis->get('str3'); $redis->get('str4'); $redis->get('str5'); $redis->get('str6'); $redis->get('str7'); $redis->get('str8'); $redis->get('str9'); $redis->get('str10'); $result = $redis->exec(); print_r($result); } catch (\Exception $e) { echo $e->getMessage(); } 結(jié)果: Array ( [0] => h [1] => e [2] => l [3] => l [4] => o [5] => w [6] => o [7] => r [8] => l [9] => d )
以上是“redis管道pipeline怎么用”這篇文章的所有內(nèi)容,感謝各位的閱讀!相信大家都有了一定的了解,希望分享的內(nèi)容對大家有所幫助,如果還想學(xué)習(xí)更多知識,歡迎關(guān)注億速云行業(yè)資訊頻道!
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。