91超碰碰碰碰久久久久久综合_超碰av人澡人澡人澡人澡人掠_国产黄大片在线观看画质优化_txt小说免费全本

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

nodejs怎么處理密集型計算的

發布時間:2020-04-20 14:45:48 來源:億速云 閱讀:316 作者:小新 欄目:web開發

nodejs怎么處理密集型計算的?相信有很多人都不太了解,今天小編為了讓大家更加了解nodejs,所以給大家總結了以下內容,一起往下看吧。

nodejs怎么處理密集型計算的

nodejs 如何處理密集型計算?

Nodejs密集型CPU解決方案

首先說一下nodejs單線程的優勢:

高性能,與php相比,避免了頻繁創建切換線程的開銷,執行更加迅速,資源占用小。

線程安全,不用擔心同一變量被多線程讀寫,造成程序崩潰。

單線程的異步和非阻塞,其實 nodejs底層訪問I/O還是多線程的,阻塞/非阻塞與異步/同步是兩個不同的概念,同步不代表阻塞,但是阻塞肯定就是同步;有點兒繞口,請聽我舉例,我去食堂打飯,我選擇了A套餐,然后工作人員幫我去配餐,如果我就站在旁邊,等待工作人員給我配餐,這種情況就稱之為同步;若工作人員幫我配餐的同時,排在我后面的人就開始點餐,這樣整個食堂的點餐服務并沒有因為我在等待A套餐而停止,這種情況就稱之為非阻塞。這個例子就簡單說明了同步但非阻塞的情況。再如果我在等待配餐的時候去買飲料,等聽到叫號再回去拿套餐,此時我的飲料也已經買好,這樣我在等待配餐的同時還執行了買飲料的任務,叫號就等于執行了回調,就是異步非阻塞了。如果我在買飲料的時候,已經叫我的號讓我去拿套餐,可是我等了好久才拿到飲料,所以我可能在大廳叫我的餐號之后很久才拿到A套餐,這也就是單線程的阻塞情況。

多線程:

線程是cpu調度的一個基本單位,一個cpu只能執行一個線程任務。

nodejs也可以執行多行程任務,例如引用TAGG/TAGG2模塊,但是不論是tagg/tagg2都是利用pthread庫和V8::Isolate類來實現js多線程功能的,根據規則我們在線程里執行的函數無法使用nodejs的核心api,例如fs,crypto模塊,所以還是有很大的局限性。

多進程:

在支持html5的瀏覽器里,我們可以使用webworker來將一些耗時的計算丟入worker進程中執行,這樣主進程就不會阻塞,用戶也不會有卡頓的感覺。

這里我們需要利用nodejs的child_process模塊,child_process提供了fork方法,可以啟動一個nodejs文件,將它視作worker進程,worker 工作完畢后,會把結果send給主進程,然后worker自動退出,這樣我們就利用了多進程解決了主線程阻塞的問題。

var express = require('express');
var fork = require('child_process').fork;
var app = express();
app.get('/', function(req, res){
  var worker = fork('./work.js') //創建一個工作進程
  worker.on('message', function(m) {//接收工作進程計算結果
          if('object' === typeof m && m.type === 'fibo'){
                   worker.kill();//發送殺死進程的信號
                   res.send(m.result.toString());//將結果返回客戶端
          }
  });
  worker.send({type:'fibo',num:~~req.query.n || 1});
  //發送給工作進程計算fibo的數量
});
app.listen(7878);

我們通過express監聽7878端口,對每個用戶的請求都會去fork一個子進程,通過調用worker.send方法將參數n傳遞給子進程,同時監聽子進程發送消息的message事件,將結果響應給客戶端。

下面是被fork的work.js文件內容:

var fibo = function fibo (n) {//定義算法
   return n > 1 ? fibo(n - 1) + fibo(n - 2) : 1;
}
process.on('message', function(m) {
//接收主進程發送過來的消息
          if(typeof m === 'object' && m.type === 'fibo'){
                  var num = fibo(~~m.num);
                  //計算jibo
                  process.send({type: 'fibo',result:num})
                  //計算完畢返回結果       
          }
});
process.on('SIGHUP', function() {
        process.exit();//收到kill信息,進程退出
});

我們先定義函數fibo用來計算斐波那契數組,然后監聽了主線程發來的消息,計算完畢之后將結果send到主線程。同時還監聽process的SIGHUP事件,觸發此事件就進程退出。

這里我們有一點需要注意,主線程的kill方法并不是真的使子進程退出,而是會觸發子進程的SIGHUP事件,真正的退出還是依靠process.exit()。

總結:

使用child_process模塊的fork方法確實可以讓我們很好的解決單線程對cpu密集型任務的阻塞問題,同時又沒有tagg包那樣無法使用Node.js核心api的限制。

單線程異步的Node.js不代表不會阻塞,在主線程做過多的任務可能會導致主線程的卡死,影響整個程序的性能,所以我們要非常小心的處理大量的循環,字符串拼接和浮點運算等cpu密集型任務,合理的利用各種技術把任務丟給子線程或子進程去完成,保持Node.js主線程的暢通。

線程/進程的使用并不是沒有開銷的,盡可能減少創建和銷毀線程/進程的次數,可以提升我們系統整體的性能和出錯的概率。

以上就是nodejs怎么處理密集型計算的的詳細內容了,看完之后是否有所收獲呢?如果想了解更多相關內容,歡迎來億速云行業資訊!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

庆元县| 会泽县| 景谷| 鹿邑县| 织金县| 永定县| 内江市| 巴南区| 日喀则市| 陵川县| 广西| 堆龙德庆县| 墨江| 美姑县| 五河县| 青河县| 东城区| 道孚县| 石台县| 洛川县| 抚州市| 治多县| 泰宁县| 河西区| 枝江市| 古浪县| 海门市| 平南县| 建昌县| 新乡县| 日土县| 车险| 永新县| 上高县| 文登市| 大邑县| 龙州县| 桑日县| 龙门县| 柳河县| 通化市|