自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

一起聊一聊如何計算 Node.js GC 負(fù)載

開發(fā) 前端
操作系統(tǒng)本身會計算每隔線程的 CPU 耗時,所以我們可以通過系統(tǒng)獲取這個數(shù)據(jù),然后計算出線程的 CPU 負(fù)載。

在 Node.js 中,我們關(guān)注的比較的是 CPU 負(fù)載,但是在有 GC 的語言中,GC 負(fù)載也是需要關(guān)注的一個指標(biāo),因為 GC 過高會影響我們應(yīng)用的性能。本文介紹關(guān)于 GC 負(fù)載的一些內(nèi)容。

如何獲取 GC 耗時

操作系統(tǒng)本身會計算每隔線程的 CPU 耗時,所以我們可以通過系統(tǒng)獲取這個數(shù)據(jù),然后計算出線程的 CPU 負(fù)載。但是 GC 不一樣,因為 GC 是應(yīng)用層的一個概念,操作系統(tǒng)是不會感知的,在 Node.js 里,具體來說,是在 V8 里,也沒有 API 可以直接獲取 GC 的耗時,但是 V8 提供了一些 GC 的鉤子函數(shù),我們可以借助這些鉤子函數(shù)來計算出 GC 的負(fù)載。其原理和 CPU 負(fù)載類似。V8 提供了以下兩個鉤子函數(shù),分別在 GC 開始和結(jié)束時會執(zhí)行。

Isolate::GetCurrent()->AddGCPrologueCallback();
Isolate::GetCurrent()->AddGCEpilogueCallback();

通過這兩個函數(shù),我們就可以得到每一次 GC 的耗時,再不斷累積就可以計算出 GC 的總耗時,從而計算出 GC 負(fù)載。下面看一下核心實現(xiàn)。

static void BeforeGCCallback(Isolate* isolate,
                             v8::GCType gc_type,
                             v8::GCCallbackFlags flags,
                             void* data) {
    GCLoad* gc_load = static_cast<GCLoad*>(data);
    if (gc_load->current_gc_type != 0) {
        return;
    }
    gc_load->current_gc_type = gc_type;
    gc_load->start_time = uv_hrtime();
}

static void AfterGCCallback(Isolate* isolate,
                            v8::GCType gc_type,
                            v8::GCCallbackFlags flags,
                            void* data) {
    GCLoad* gc_load = static_cast<GCLoad*>(data);
    if (gc_load->current_gc_type != gc_type) {
        return;
    }
    gc_load->current_gc_type = 0;
    gc_load->total_time += uv_hrtime() - gc_load->start_time;
    gc_load->start_time = 0;
}

void GCLoad::Start(const FunctionCallbackInfo<Value>& args) {
    GCLoad* obj = ObjectWrap::Unwrap<GCLoad>(args.Holder());
    Isolate::GetCurrent()->AddGCPrologueCallback(BeforeGCCallback, static_cast<void*>(obj));
    Isolate::GetCurrent()->AddGCEpilogueCallback(AfterGCCallback, static_cast<void*>(obj));
}

可以看到思路很簡單,就是注冊兩個 GC 鉤子函數(shù),然后在 GC 開始鉤子中記錄開始時間,然后在 GC 結(jié)束鉤子中記錄結(jié)束時間,并算出一次 GC 的耗時,再累加起來,這樣就可以得到任意時刻 GC 的總耗時,但是拿到總耗時如何計算出 GC 負(fù)載呢?

如何計算 GC 負(fù)載

負(fù)載 = 過去一段時間內(nèi)的消耗 / 過去的一段時間值,看看如何計算 GC 負(fù)載。

class GCLoad {
    lastTime;
    lastTotal;
    binding = null;
    start() {
        if (!this.binding) {
            this.binding = new binding.GCLoad();
            this.binding.start();
        }
    }
    stop() {
        if (this.binding) {
            this.binding.stop();
            this.binding = null;
        }
    }
    load() {
        if (this.binding) {
            const { lastTime, lastTotal } = this;
            const now = process.hrtime();
            const total = this.binding.total();
            this.lastTime = now;
            this.lastTotal = total;
            if (lastTime && lastTotal) {
                const cost = total - lastTotal;
                const interval = (now[0] - lastTime[0]) * 1e6 + (now[1] - lastTime[1]) / 1e3;
                return cost / interval;
            }
        }
    }
    total() {
        if (this.binding) {
            return this.binding.total();
        }
    }
}

計算算法也很簡單,就是記錄上次的時間和 GC 耗時,然后下次需要記錄某個時刻的 GC 負(fù)載時,就拿當(dāng)前的耗時減去上次的耗時,并拿當(dāng)前的時間減去上次的時間,然后得到過去一段時間內(nèi)的耗時和過去的時間大小,一處就得到 GC 負(fù)載了。

使用

下面看看如何使用。

const { GCLoad } = require('..');
const gcLoad = new GCLoad();
gcLoad.start();
setInterval(() => {
    for (let i = 0; i < 1000; i++) {
        new Array(100);
    }
    gc();
    console.log(gcLoad.load());
}, 3000);

執(zhí)行上面代碼會(node --expose-gc demo.js) 在我電腦上輸出如下。

0.004235378248715853
0.004100483670865412
0.0017808558192331187
0.002371772559838465
0.0024768595957239477

這樣就可以得到了應(yīng)用的 GC 負(fù)載。

完整代碼參考 https://github.com/theanarkh/nodejs-native-gc-load。

責(zé)任編輯:姜華 來源: 編程雜技
相關(guān)推薦

2023-09-29 08:58:38

2023-08-14 08:38:26

反射reflect結(jié)構(gòu)體

2021-08-07 07:56:59

Node邏輯對象

2024-02-06 08:58:23

開源項目my-tv

2022-08-26 00:35:31

Java工作流系統(tǒng)

2022-08-22 09:20:05

Kubernetes工作負(fù)載管理

2022-10-08 11:33:56

邊緣計算云計算

2021-10-12 23:45:43

NodeJs事件

2020-07-16 14:40:23

大數(shù)據(jù)計算框架

2023-02-07 06:42:24

Pulsar負(fù)載均衡

2020-11-05 09:27:48

JavaScript開發(fā)技術(shù)

2022-02-16 10:25:36

邊緣計算數(shù)據(jù)中心網(wǎng)絡(luò)

2020-12-29 05:33:40

TomcatSpringBoot代碼

2014-04-01 11:02:00

Node.jsWeb Socket聊天程序

2018-05-16 08:58:04

用戶畫像存儲

2022-03-06 20:35:41

并發(fā)串行CAP

2019-01-31 07:16:06

2023-09-22 17:36:37

2021-01-28 22:31:33

分組密碼算法

2020-05-22 08:16:07

PONGPONXG-PON
點贊
收藏

51CTO技術(shù)棧公眾號