摘要:當(dāng)子進(jìn)程都完成了,主進(jìn)程開始繼續(xù)業(yè)務(wù)。是子進(jìn)程的句柄子進(jìn)程句柄向自己管道里寫內(nèi)容子進(jìn)程句柄從自己的管道里面讀取信息這里是子進(jìn)程哦貼上運(yùn)行結(jié)果喔,通訊是這樣的。我們再看看創(chuàng)建進(jìn)程時第二個參數(shù)的說明,重定向子進(jìn)程的標(biāo)準(zhǔn)輸入和輸出。
進(jìn)程管理模塊
介紹看這里 swoole的process
大家可以先看看自己的swoole版本,在命令行里面敲
php --ri swoole
更多的php命令行使用,大家學(xué)習(xí) php命令行參數(shù)
ok 我們直奔主題
怎么用
不多說,直接上代碼
start(); echo PHP_EOL . $pid;// } function callback_function_we_write(swoole_process $worker){ echo PHP_EOL; var_dump($worker); echo PHP_EOL; }
運(yùn)行結(jié)果如下
5445 object(swoole_process)#1 (3) { ["pipe"]=> int(3) ["callback"]=> string(26) "callback_function_we_write" ["pid"]=> int(5445) } 5446 object(swoole_process)#2 (3) { ["pipe"]=> int(5) ["callback"]=> string(26) "callback_function_we_write" ["pid"]=> int(5446) }
可以看到,我們使用 new swoole_process 創(chuàng)建進(jìn)程,這里需要一個參數(shù),也就是回調(diào)函數(shù)
當(dāng)我們使用 $process->start()執(zhí)行后,返回這個進(jìn)程的pid ,也就是 $pid.
此時子進(jìn)程啟動,調(diào)用回調(diào)函數(shù),并傳一個參數(shù) 也就是 swoole_process 類型的 $worker
我故意輸出了 $worker 看看里面有什么,結(jié)果有三個屬性
pipe 進(jìn)程的管道id 這個等說道進(jìn)程間通信的時候再聊
pid 就是當(dāng)前子進(jìn)程的 pid 啦
callback 這個是我們自己寫的回調(diào)函數(shù)名
到這里,我們就可以用多進(jìn)程玩耍了,
比如,我們可以測試多進(jìn)程的運(yùn)行速度
start(); } function callback_function_we_write(swoole_process $worker){ for($i=0;$i<100000000;$i++){} echo PHP_EOL . time() ; }
我本機(jī)運(yùn)行結(jié)果
1435563435 // 開始時間
1435563438 //進(jìn)程1 結(jié)束時間
1435563440 //進(jìn)程2 結(jié)束時間
1435563440 //進(jìn)程3 結(jié)束時間
算三次 用了5s (其實一般是4s)
再玩一次
我本機(jī)運(yùn)行結(jié)果
1435563704
1435563712這次用了8s
做了這些,我想說明一個問題
并不是說 單進(jìn)程 要花8s 做完的活,我們用3個進(jìn)程就能將時間縮小三倍了
嘛,因為這是我以前的誤區(qū)
多進(jìn)程還可以這樣玩
start(); sleep(2); } while(1){ $ret = swoole_process::wait(); if ($ret){// $ret 是個數(shù)組 code是進(jìn)程退出狀態(tài)碼, $pid = $ret["pid"]; echo PHP_EOL."Worker Exit, PID=" . $pid . PHP_EOL; }else{ break; } } function methodOne(swoole_process $worker){// 第一個處理 echo $worker->callback .PHP_EOL; } function methodTwo(swoole_process $worker){// 第二個處理 echo $worker->callback .PHP_EOL; } function methodThree(swoole_process $worker){// 第三個處理 echo $worker->callback .PHP_EOL; }我多加的sleep是為了運(yùn)行時看得更清楚,你也可以去掉
這里我使用了 swoole_process::wait() 詳解
目的是當(dāng)子進(jìn)程結(jié)束后,主進(jìn)程能夠知道。我們來想一個情景
過節(jié)了,媽媽要做飯,一看廚房里缺了 油,鹽,糖,味精,十三香。于是吩咐兒子去小賣部買點回來。廚房這邊也不能閑著,老媽要繼續(xù)洗菜,切菜。等到調(diào)料買回來了,菜也洗好,切好了,開始炒,這邊炒好了一個菜,就要立刻送到餐桌上。這個情景里面,顯然使用了多進(jìn)程,并且各進(jìn)程做的不是同樣的事情。當(dāng)子進(jìn)程都完成了,主進(jìn)程開始繼續(xù)業(yè)務(wù)。
現(xiàn)在有了一個問題,就拿上面的情景來說,兒子去買調(diào)味料,如果發(fā)現(xiàn)鹽沒有了,或者錢不夠了怎么辦,如何與媽媽聯(lián)系呢? 這就是下面要說的 進(jìn)程間的通信
進(jìn)程間的通信Process 的通信方式有兩種
管道
swoole_process->write(string $data);
swoole_process->read(int $buffer_size=8192);消息隊列
swoole_process->useQueue();
swoole_process->push(string $data);
swoole_process->pop(int $maxsize = 8192);我們先說說管道
管道通訊這里我們要再次的提及進(jìn)程的創(chuàng)建 new swoole_process
大家請看這里 進(jìn)程的創(chuàng)建
第一個參數(shù)是回調(diào)函數(shù),不說了
第二個參數(shù)含義等會我會結(jié)合例子來說
第三個參數(shù)是默認(rèn)的 true,意思是創(chuàng)建管道,大家還記得回調(diào)函數(shù)里我特意將$worker輸出看到的內(nèi)容嗎?object(swoole_process)#1 (3) { ["pipe"]=> int(3) ["callback"]=> string(26) "callback_function_we_write" ["pid"]=> int(5445) }關(guān)鍵是這里的 pipe 這個就是本進(jìn)程的管道id
我們可以這樣理解每次創(chuàng)建一個進(jìn)程后,就會隨之創(chuàng)建一個管道,主進(jìn)程想和哪一個進(jìn)程通信,就向那個進(jìn)程的管道寫入/讀取數(shù)據(jù)。
ok,我們看看代碼
start(); $workers[$pid] = $process;//將每一個進(jìn)程的句柄存起來 } // 這里是主進(jìn)程哦。 foreach($workers as $pid => $process){// $process 是子進(jìn)程的句柄 $process->write("hello worker[$pid] ");//子進(jìn)程句柄向自己管道里寫內(nèi)容 $process->write($data); echo "From Worker: ".$process->read();//子進(jìn)程句柄從自己的管道里面讀取信息 $process->read(); echo PHP_EOL.PHP_EOL; } function workerFunc(swoole_process $worker){//這里是子進(jìn)程哦 $recv = $worker->read(); echo PHP_EOL. "From Master: $recv "; //send data to master $worker->write("hello master , this pipe is ". $worker->pipe ."; this pid is ".$worker->pid." "); sleep(2); $worker->exit(0); }貼上運(yùn)行結(jié)果
From Master: hello worker[8205] From Worker: hello master , this pipe is 3; this pid is 8205 From Master: hello worker[8206] From Worker: hello master , this pipe is 5; this pid is 8206喔,通訊是這樣的。
首先 將所有的子進(jìn)程的句柄都存到 主進(jìn)程的一個數(shù)組里,數(shù)組下標(biāo)就是pid。
當(dāng)主進(jìn)程想和哪個進(jìn)程通訊,就使用那個句柄向?qū)?yīng)管道里面 寫/讀 數(shù)據(jù),這樣就實現(xiàn)了進(jìn)程間的通訊。接著,我們稍微改一下,看看運(yùn)行效果
$redirect_stdout = true;// 重定向輸出 注意 這次我改成 true 了,其他沒變 $worker_num = 2;//進(jìn)程數(shù)量 $workers = [];//存放進(jìn)程用的 for($i = 0; $i < $worker_num; $i++){ $process = new swoole_process("workerFunc",$redirect_stdout ); $pid = $process->start(); $workers[$pid] = $process;//將每一個進(jìn)程的句柄存起來 } // 這里是主進(jìn)程哦。 foreach($workers as $pid => $process){// $process 是子進(jìn)程的句柄 $process->write("hello worker[$pid] ");//子進(jìn)程句柄向自己管道里寫內(nèi)容 $process->write($data); echo "From Worker: ".$process->read();//子進(jìn)程句柄從自己的管道里面讀取信息 $process->read(); echo PHP_EOL.PHP_EOL; } function workerFunc(swoole_process $worker){//這里是子進(jìn)程哦 $recv = $worker->read(); echo PHP_EOL. "From Master: $recv "; //send data to master $worker->write("hello master , this pipe is ". $worker->pipe ."; this pid is ".$worker->pid." "); sleep(2); $worker->exit(0); }輸出結(jié)果
From Worker: From Master: hello worker[8007] From Worker: From Master: hello worker[8008]誒,不一樣了有沒有。我們再看看創(chuàng)建進(jìn)程時第二個參數(shù)的說明
$redirect_stdin_stdout,重定向子進(jìn)程的標(biāo)準(zhǔn)輸入和輸出。 啟用此選項后,在進(jìn)程內(nèi)echo將不是打印屏幕,而是寫入到管道。讀取鍵盤輸入將變?yōu)閺墓艿乐凶x取數(shù)據(jù)。 默認(rèn)為阻塞讀取。
我來說明一下,因為創(chuàng)建的時候指定了true,子進(jìn)程中echo的內(nèi)容就到了管道里面,而不是打印在屏幕上(這一點類似于php的ob緩存機(jī)制,大家想象一下)
消息隊列
前面說了,進(jìn)程的通訊是通過從管道里面讀/寫數(shù)據(jù)實現(xiàn)的,而 子進(jìn)程 里 echo 的內(nèi)容被 重定向到管道里面了,所以,主進(jìn)程從管道里讀到的內(nèi)容,就是 子進(jìn)程中 echo 的 內(nèi)容。
也就造成了上面的 輸出結(jié)果。我先來個鏈接 利用PHP操作Linux消息隊列完成進(jìn)程間通信
重點是這個文章里面的兩個鏈接文章啊,大家等會看看
還有一個命令ipcs -q 查看當(dāng)前的消息隊列
這部分 下次討論
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/20990.html
摘要:不多說,上代碼這段代碼出自消息隊列我想說五個點的創(chuàng)建默認(rèn)是創(chuàng)建的管道,當(dāng)想用消息隊列時,記得把參數(shù)設(shè)成其實我發(fā)現(xiàn)不寫也行要在的之前調(diào)用,方法默認(rèn)是阻塞的一定一定要寫這里坑死不少人還有第五點注意事項,我接下來重點說,因為這個點卡了我好久。 不多說,上代碼
摘要:原先用的多線程實現(xiàn)的支付結(jié)果回調(diào)服務(wù),在后期運(yùn)行中出現(xiàn)了服務(wù)停止的問題,在學(xué)習(xí)的過程中,發(fā)現(xiàn)可以用的進(jìn)程管理模塊實現(xiàn)多線程的功能,并且使用定時器功能實現(xiàn)進(jìn)程監(jiān)控在子進(jìn)程退出的時候進(jìn)行重啟。 原先用PHP的Pthread多線程實現(xiàn)的支付結(jié)果回調(diào)服務(wù),在后期運(yùn)行中出現(xiàn)了服務(wù)停止的問題,在學(xué)習(xí)swoole的過程中,發(fā)現(xiàn)可以用swoole的Process進(jìn)程管理模塊實現(xiàn)多線程的功能,并且使用s...
摘要:消息隊列更常見的用途是主進(jìn)程分配任務(wù),子進(jìn)程消費(fèi)執(zhí)行。子進(jìn)程前面加了個,這是為了防止父進(jìn)程還未往消息隊列中加入內(nèi)容直接退出。 前面幾節(jié)都是講解pcntl擴(kuò)展實現(xiàn)的多進(jìn)程程序。本節(jié)給大家介紹swoole擴(kuò)展的swoole_process模塊。 swoole多進(jìn)程 swoole_process 是swoole提供的進(jìn)程管理模塊,用來替代PHP的pcntl擴(kuò)展。 首先,確保安裝的swoole...
摘要:在中的應(yīng)用官網(wǎng)源碼解讀號外號外歡迎大家我們開發(fā)組定了一個就線下聚一次的小目標(biāo)上一篇源碼解讀反響還不錯不少同學(xué)推薦再加一篇講解一下中使用到的功能幫助大家開啟的實戰(zhàn)之旅服務(wù)器開發(fā)涉及到的相關(guān)技術(shù)領(lǐng)域的知識非常多不日積月累打好基礎(chǔ)是很難真正 date: 2017-12-14 21:34:51title: swoole 在 swoft 中的應(yīng)用 swoft 官網(wǎng): https://www.sw...
摘要:配合模塊,創(chuàng)建的子進(jìn)程可以異步的事件驅(qū)動模式。默認(rèn)為阻塞讀取。函數(shù)用于將一個加入到的事件監(jiān)聽中。為事件類型的掩碼,可選擇關(guān)閉開啟可讀可寫事件,如,,或者。在程序中使用,可以理解為在進(jìn)程中將此注冊到事件中。 Process Process是swoole內(nèi)置的進(jìn)程管理模塊,用來替代PHP的pcntl擴(kuò)展。 swoole_process支持重定向標(biāo)準(zhǔn)輸入和輸出,在子進(jìn)程內(nèi)echo不會打印屏...
閱讀 2585·2021-10-19 11:41
閱讀 2423·2021-09-01 10:32
閱讀 3382·2019-08-29 15:21
閱讀 1762·2019-08-29 12:20
閱讀 1170·2019-08-29 12:13
閱讀 607·2019-08-26 12:24
閱讀 2524·2019-08-26 10:26
閱讀 840·2019-08-23 18:40