js 獲取father_(原創)Node.JS實戰26:強大的工作池。收藏吧!你一定會用的到。...

在實際項目中,如果遇到需要大計算量的操作,按需fork(分叉)其實不是一個好的選擇。

因為fork的子進程也是V8(NodeJS的核心引擎)的新實例,每創建一個新實例,需要約30毫秒啟動時間,和至少10MB的初始內存。

也就是說,創建進程是有代價的,你不能創建太多,也不能頻繁創建。那樣,達不到提高進程效率的目的。

那么,該如何高效優雅的使用子進程呢?工作池!

工作池!

合理的辦法是創建一個可用的工作池,在池中存放足夠多的進程,并可以隨時分配使用。

我們對上一節講的內容進行升級:當父進程發送一個任務給子進程時,子進程執行任務。并將結果向主進程反饋。

在父進程中,需要的代碼會是這樣的:

function doWork(job,cb){var child = cp.fork("./worker");//發送工作給子進程child.send(job);//希望子進程返回一個確切的消息child.once("message",function(result){cb(null,result);})
}

嗯...這樣講有些凌亂,這一章比較復雜,最好的辦法,還是寫一個完整的代碼,做為例子:

aeec6c154f8f34a01167aca481af8454.png

1、father.js,主進程

var http = require("http");
var makePool = require("./pooler");
var runJob = makePool("./worker");http.createServer(function(req,res){runJob("some dummy job",function(er,data){console.log("father callback get:",data);if(er){return res.end("get an error:"+er.message)}res.end("work pool");})}).listen(8000)

當有客端訪問時,觸發runjob,開始啟行工作。

2、worker.js

process.on("message",function(job){console.log("worker get msg:",job);for(var i=0;i<10;i++){console.log("worker send:",job,i);process.send("finish job:"+job+i);}})

收到father主進程發來的消息時,使用process.send()方法調用子進程,向工作池發出工作任務。

3、pool.js(工作池)

接收worker消息,用工作池完成操作,并反饋給主程序。

代碼中做了詳細的注釋 ,就不單獨對代碼做解析了:

var cp = require("child_process");
//獲取CPU數量,有幾個CPU就創建幾個子進程,這樣就可以最大化的利用機器性能
var cpus = require("os").cpus().length;//模塊導出函數
module.exports = function(workModule){//等待任務隊列,當工作任務被下發,但沒有閑工作進程時,放到此隊列var awaiting = [];//存放準備就緒的工作進程var readyPool = [];//當前的工作子進程數量(工作池的大小)var poolSize = 0;return function doWork(job,cb){//如果工作池數量已經最大,并且沒有準備就緒的工作子進程,也就是所有工作子進程都在工作中,那么:排隊等待if(!readyPool.length && poolSize >cpus){//壓入到等待隊列,等待后續處理return awaiting.push([dowork,job.cb]);}//取得一個可用的工作子進程,或fork(分叉)一個新的子進程(增加工作池的大小)var child = readyPool.length ? readyPool.shift() : (poolSize++, cp.fork(workModule));{//子進程是否完成回調的標記var cbTriggered = false;//初始階段,移除子進程上的監聽,確保每個子進程只擁有一次監聽child.removeAllListeners();//錯誤child.once("error",function(err){//未回調if(!cbTriggered){//回調返回為錯誤cb(err);//回調標識改為true:已回調cbTriggered = true;} //結束子進程child.kill();//這里不用操作工作池poolSize--,因為kill會觸發exit事件,在exit事件中操作工作池});//子進程退出了(不明原因的意外退出、被kill()等都觸發)child.once("exit",function(code,signal){//未回調if(!cbTriggered){//回調,返回信息cb(new Error("Child exited with code:"+code))}//工作池(正在工作的子進程數)大小減一poolSize --;//退出的子進程,是否在準備好的子進程數組中var childIdx = readyPool.indexOf(child);if(childIdx > -1){//從準備好的子進程數組中移除readyPool.splice(childIdx,1);}})//獲取父進程發來的消息child.on("message",function(msg){console.log("pool get msg:",msg);cb(null,msg);cbTriggered = true;readyPool.push(child);//如何等待區有內容,處理之if(awaiting.length){setImmediate.apply(null,awaiting.shift());}//向父進程發送消息}).send(job);}//child區域結束}
}

執行效果

1b6fabc7b6b599c64fcc4c7ff81d447e.png

圖中展示的是工作流程,可見此種方法可以達到我們的預期,工作池很OK。

對于實際編程中遇到的消耗比較大的情況,使用此種方法可以極大的提高效率,且本文已經將工作池寫成了模塊(pooler.js)

建議收藏,nodejs開發,在某個時候一定會遇到適合的場景的。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/372949.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/372949.shtml
英文地址,請注明出處:http://en.pswp.cn/news/372949.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

具有ReadWriteLock的Java并發

編寫多線程Java應用程序并不是小菜一碟。 必須格外小心&#xff0c;因為同步不良會使您的應用程序一s不振。 JVM堆由所有線程共享。 如果多個線程需要同時使用相同的對象或靜態類變量&#xff0c;則必須謹慎管理對共享數據的線程訪問。 從1.5版開始&#xff0c;JSDK中包含了在并…

修復steam服務器失敗,steam服務器鏈接失敗

steam服務器鏈接失敗 內容精選換一換當NTP服務器異常時產生該告警。當NTP服務器異常消除時&#xff0c;該告警恢復。主OMS節點配置的NTP服務器異常&#xff0c;可能會導致主OMS節點與外部服務器不能同步時間&#xff0c;集群時間可能會產生飄移。NTP服務器網絡異常。與NTP服務器…

qemu-kvm簡單使用

qemu-kvm主要有以下幾個選項: -snapshot: 創建快照-m: 指定內存大小-smp: 指定處理器個數-cpu: 指定CPU類型-name: 設置虛擬機名稱-vnc: 使用vnc連接-boot: 指定啟動相關的選項-net: 指定網卡相關的選項-drive: 指定硬盤/光盤相關的選項qemu-kvm -m 128 -name first -smp 2 -dr…

將jar添加到發布目錄_第32批免購置稅新能源車型目錄發布;通用BEV3平臺將入華...

1、第32批免購置稅新能源車型目錄發布&#xff0c;幾何X/理想ONE等283款車型入選6月2日&#xff0c;工信部發布《免征車輛購置稅的新能源汽車車型目錄(第三十二批)》&#xff0c;共有283款新能源車型入選。其中新能源乘用車方面包括&#xff0c;一汽大眾Q2L/e-BORA、東風風神E7…

HPROF –內存泄漏分析教程

本文將為您提供有關如何通過生成和分析Sun HotSpot JVM HPROF堆轉儲文件來分析JVM內存泄漏問題的教程。 一個現實的案例研究將用于此目的&#xff1a;Weblogic 9.2內存泄漏影響Weblogic Admin服務器。 環境規格 Java EE服務器&#xff1a;Oracle Weblogic Server 9.2 MP1 中…

mq服務器與客戶端消息同步,使用 ActiveMQ 實現JMS 異步調用

目錄簡介服務之間的同步調用&#xff0c;可以使用 HTTP 或 RPC 來完成&#xff0c;但并非所有的調用都需要同步&#xff0c;有些場景下&#xff0c;當客戶端調用服務端時&#xff0c;并不需要等待服務端做出響應&#xff0c;此時就應該使用異步調用。異步調用的常用方式是基于 …

多個數字數組_七個問題幫助初學者深入理解Java數組

短文漲姿勢&#xff0c;看了不白看&#xff0c;不關注等啥&#xff1f;幾乎所有的高級語言當中&#xff0c;都提供了一種叫做”數組”的東西&#xff0c;Java語言當然也不例外。我們通過數組可以很方便的存儲和管理一組數據。因為在Java語言當中使用數組非常的方便&#xff0c;…

java 異常練習題1

建立exception包&#xff0c;建立Bank類&#xff0c;類中有變量double balance表示存款,Bank類的構造方法能增加存款&#xff0c;Bank類中有取款的發方法withDrawal(double dAmount),當取款的數額大于存款時,拋出InsufficientFundsException,取款數額為負數&#xff0c;拋出Nag…

大話設計模式讀書筆記--6.原型模式

簡單的復制粘貼極有可能造成重復代碼的災難, 但是java中提供了克隆的功能, 如果一個對象創建過程復雜,又要頻繁使用, 在初始化信息不發生變化的情況下,應當采取克隆而不是new一個對象 定義 原型模式: 用原型實例指定創建對象的種類,并且通過拷貝這些原型創建新的對象 也就是說,…

Java 7#8:測試臺上的NIO.2文件通道

關于新JDK 7功能的另一篇博客文章。 這次我正在寫有關新的AnsynchronousFileChannel類的文章。 我將在兩周內深入分析新的JDK 7功能&#xff0c;并決定連續編號我的帖子。 只是為了確保我不會感到困惑&#xff1a;-)這是我關于Java 7的第七篇文章&#xff08;我承認–碰巧–這也…

5頁面title樣式修改_認識html:實現網站頁面是這么簡單的一回事

互聯網時代人們通過上網瀏覽信息&#xff0c;打開瀏覽器上網看到豐富的圖文、視頻、音樂等多媒體信息&#xff0c;一系列信息反饋和視覺沖擊之后&#xff0c;您有沒有想過&#xff0c;互聯網這么發達的時代&#xff0c;您覺得花一點點時間學會做個網站頁面不真香&#xff1f;概…

iOS指南針

前言&#xff1a; 這個小項目使用到了CoreLocation框架里面的設備朝向功能&#xff0c;對CoreLocation感興趣的可以翻一下之前的文章 在另一個博客站有朋友發現一個尷尬的問題&#xff08;圖片的東西2個方向是不對的&#xff09;&#xff0c;原諒我的大意&#xff0c;趕時間就直…

OSGI –模塊化您的應用程序

由于我是模塊化&#xff0c;低耦合&#xff0c;高凝聚力等的大力擁護者&#xff0c;所以…… 我相信這項技術是我們使用Java平臺創建應用程序的突破。 使用OSGi&#xff0c;創建高度可擴展的應用程序非常簡單&#xff0c;例如參見Eclipse IDE。 我的目的不是要深入展示該技術的…

jq的鏈式調用.end();

jq的鏈式調用.end(); 先上code <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><title>Title</title><style>li{list-style: none;width: 100px;height:20px;border:1px solid #ff0000;display: …

三、自定義視圖、視圖控制器

1.自定義視圖 自定義視圖&#xff1a;系統標準UI之外&#xff0c;自己組合而出的新的視圖。在實際開發中&#xff0c;我們經常需要自己定義視圖&#xff0c;積累自己的代碼庫。自己封裝的視圖&#xff0c;能像系統提供的UI控件一樣用于多個項目中&#xff0c;這樣可以提高我們的…

程序如何在兩個gpu卡上并行運行_深度學習分布式訓練相關介紹 - Part 1 多GPU訓練...

本篇文章主要是對深度學習中運用多GPU進行訓練的一些基本的知識點進行的一個梳理文章中的內容都是經過認真地分析&#xff0c;并且盡量做到有所考證拋磚引玉&#xff0c;希望可以給大家有更多的啟發&#xff0c;并能有所收獲介紹大多數時候&#xff0c;梯度下降算法的訓練需要較…

集成Spring和JavaServer Faces:改進的模板

隨著2.0版的發布&#xff0c;Facelet模板成為JSF規范的核心部分。 使用<ui&#xff1a;composition>和<ui&#xff1a;decorate>標記&#xff0c;可以輕松構建復雜的頁面&#xff0c;同時仍保持標記清晰。 模板在創建HTML表單時特別有用&#xff0c;但是不幸的是&a…

whmcs模板路徑

whmcs網站根目錄 比如你的域名是server.nongbin.vip&#xff0c;你需要cd /home/wwwroot/server.nongbin.vip&#xff0c;該目錄下然后&#xff0c;cd template/ 給文件夾下就是你上傳的模板文件夾轉載于:https://www.cnblogs.com/nongbin/p/6412108.html

系統英偉達gpu驅動卸載_繞過CPU,英偉達讓GPU直連存儲設備

英偉達最近發布了一個新的GPUDirect Storage&#xff0c;暫且叫做GPU直連存儲&#xff0c;讓GPU直接連到NVMe存儲設備上。這一方案用到了RDMA設備來把數據從閃存存儲轉移到GPU本地的內存里&#xff0c;無需經過CPU還有系統內存。如果這一舉措順利的話&#xff0c;英偉達就能擺脫…

37、EnumSet詳解

EnumSet類也是有順序的&#xff0c;EnumSet按照枚舉值在Enum類內定義的順序決定集合元素的順序 EnumSet在內部已位向量的形式存儲&#xff0c;這種存儲方式非常緊湊、搞笑&#xff0c;因此EnumSet占用內存很小&#xff0c;而且運行效率很好。 EnumSet集合不允許加入null元素 En…