官方文檔建議的 Buffer Pool 命中率公式:100 - (Innodb_buffer_pool_reads / Innodb_buffer_pool_read_requests) * 100。但 SHOW ENGINE INNODB STATUS 顯示的 Buffer pool hit rate XXX/1000 計算邏輯不同。本文從源碼層面解析兩者差異與適用場景。
Hit Ratio = 100 - (Innodb_buffer_pool_reads / Innodb_buffer_pool_read_requests) * 100
來源:mysql->status->Innodb_buffer_pool_reads / read_requests 為啟動以來的累計計數器。
檔案:storage/innobase/buf/buf0buf.c 函式 buf_print_io()
void buf_print_io(...) {
if (buf_pool->n_page_gets > buf_pool->n_page_gets_old) {
fprintf(file, "Buffer pool hit rate %lu / 1000\n",
(ulong) (1000 - ((1000 * (buf_pool->n_pages_read - buf_pool->n_pages_read_old))
/ (buf_pool->n_page_gets - buf_pool->n_page_gets_old))));
}
buf_pool->n_page_gets_old = buf_pool->n_page_gets;
buf_pool->n_pages_read_old = buf_pool->n_pages_read;
}
對應結構體 buf_block_struct(buf0buf.h):
n_page_gets:頁面獲取總數(含自適應雜湊索引命中)n_pages_read:實際磁碟讀取頁面數_old 變數:上次列印時的快照值ib_bp_hit = 1000 - ( (t2.iReads - t1.iReads) / (t2.iReadRequests - t1.iReadRequests) ) * 1000
t1, t2:兩個時間點(間隔 ≥ 30 秒)iReads = Innodb_buffer_pool_readsiReadRequests = Innodb_buffer_pool_read_requests| 維度 | 官方累計公式 | 源碼區間公式 |
|---|---|---|
| 數據基礎 | 啟動至今累計 | 兩採樣點差值 |
| 反映範圍 | 整體歷史表現 | 當下/近期表現 |
| 敏感度 | 低(大分母稀釋波動) | 高(能捕捉抖動) |
| 適用場景 | 容量規劃、長期趨勢 | 故障排查、效能抖動偵測 |
Innodb_buffer_pool_reads、read_requests。Innodb_buffer_pool_wait_free、Innodb_log_waits 綜合判斷 Buffer Pool 壓力。srv_export_innodb_status()(Srv0srv.c)輸出的其他關鍵指標。結論:區間差值法更貼近源碼邏輯,能及時發現效能抖動;累計法適合長期趨勢報表。監控系統建議兩者並存。