一、基礎內存模型
-
指針包裝
- 所有 JSON 值(標量、對象、數組、字符串等)至少占用 8 字節,用于存儲一個帶類型標記的指針。
-
標量與空容器
null
、true
、false
、小整數(靜態緩存)、空字符串、空數組、空對象 均不分配額外內存,僅用上述 8 字節指針指向靜態實例。
二、字符串存儲
-
額外字節消耗 = 字符串長度
-
示例:存儲
"bar"
(3 字節)JSON.SET foo . '"bar"' JSON.DEBUG MEMORY foo → 11 字節(8 + 3)
三、數組的幾何增長
-
初始容量:4
-
元數據:16 字節(8 字節容量,8 字節當前長度)
-
指針包裝:8 字節
-
元素指針數組:
capacity × 8
字節 -
示例:
- 1–4 個元素 → 8 + 16 + 4×8 = 56 字節
- 第 5 個元素觸發擴容至 8 → 8 + 16 + 8×8 = 88 字節
四、磁盤文件存儲對比
測試文件 | 原始 JSON 大小 | RedisJSON 占用 | MessagePack 占用 |
---|---|---|---|
pass-100.json (380 B) | 381 B | 1,069 B | 140 B |
pass-jsonsl-1.json (1.4 KB) | 1,387 B | 2,190 B | 757 B |
pass-json-parser-0000.json (3.7 KB) | 3,718 B | 5,469 B | 2,393 B |
pass-jsonsl-yahoo2.json (22 KB) | 22,466 B | 26,901 B | 16,869 B |
pass-jsonsl-yelp.json (46 KB) | 46,333 B | 57,513 B | 35,529 B |
提示:刪除數組或對象中的元素并不會自動釋放已分配的內存。
五、全局字符串重用機制
- Redis 內核對相同字符串內容只存一份物理內存,多處引用。
JSON.DEBUG MEMORY
報告時仍按邏輯實例“各自”計算,可能顯著高于實際物理占用。
六、調優建議
- 小字符串優先:盡量避免超長文本字段,或分割存儲;
- 合理預分配數組:對大數組可預先
JSON.SET
一個空數組并擴容到合適長度,減少中間擴容次數; - 字段重用:對重復出現的關鍵字或枚舉值,依賴 Redis 全局字符串重用降低物理占用;
- 監控內存:定期使用
JSON.DEBUG MEMORY
與MEMORY USAGE
對比物理報告,識別潛在內存膨脹; - 版本升級:關注新版 RedisJSON 的優化與內存改進,及時升級。
通過以上剖析與對比,您可以更精準地評估和控制 RedisJSON 在生產環境中的內存消耗,并制定高效的存儲與訪問策略。