整數集合的升級策略有兩個好處, 一個是提升整數集合的靈活性, 另一個是盡可能地節約內存。
## 提升靈活性
因為 C 語言是靜態類型語言, 為了避免類型錯誤, 我們通常不會將兩種不同類型的值放在同一個數據結構里面。
比如說, 我們一般只使用?`int16_t`?類型的數組來保存?`int16_t`?類型的值, 只使用?`int32_t`?類型的數組來保存?`int32_t`?類型的值, 諸如此類。
但是, 因為整數集合可以通過自動升級底層數組來適應新元素, 所以我們可以隨意地將?`int16_t`?、?`int32_t`?或者?`int64_t`?類型的整數添加到集合中, 而不必擔心出現類型錯誤, 這種做法非常靈活。
## 節約內存
當然, 要讓一個數組可以同時保存?`int16_t`?、?`int32_t`?、?`int64_t`?三種類型的值, 最簡單的做法就是直接使用?`int64_t`?類型的數組作為整數集合的底層實現。 不過這樣一來, 即使添加到整數集合里面的都是?`int16_t`?類型或者?`int32_t`?類型的值, 數組都需要使用?`int64_t`?類型的空間去保存它們, 從而出現浪費內存的情況。
而整數集合現在的做法既可以讓集合能同時保存三種不同類型的值, 又可以確保升級操作只會在有需要的時候進行, 這可以盡量節省內存。
比如說, 如果我們一直只向整數集合添加?`int16_t`?類型的值, 那么整數集合的底層實現就會一直是?`int16_t`?類型的數組, 只有在我們要將`int32_t`?類型或者?`int64_t`?類型的值添加到集合時, 程序才會對數組進行升級。
- 介紹
- 前言
- 致謝
- 簡介
- 第一部分:數據結構與對象
- 簡單動態字符串
- SDS 的定義
- SDS 與 C 字符串的區別
- SDS API
- 重點回顧
- 參考資料
- 鏈表
- 鏈表和鏈表節點的實現
- 鏈表和鏈表節點的 API
- 重點回顧
- 字典
- 字典的實現
- 哈希算法
- 解決鍵沖突
- rehash
- 漸進式 rehash
- 字典 API
- 重點回顧
- 跳躍表
- 跳躍表的實現
- 跳躍表 API
- 重點回顧
- 整數集合
- 整數集合的實現
- 升級
- 升級的好處
- 降級
- 整數集合 API
- 重點回顧
- 壓縮列表
- 壓縮列表的構成
- 壓縮列表節點的構成
- 連鎖更新
- 壓縮列表 API
- 重點回顧
- 對象
- 對象的類型與編碼
- 字符串對象
- 列表對象
- 哈希對象
- 集合對象
- 有序集合對象
- 類型檢查與命令多態
- 內存回收
- 對象共享
- 對象的空轉時長
- 重點回顧
- 第二部分:單機數據庫的實現
- 數據庫
- 數據庫鍵空間
- 重點回顧
- RDB 持久化
- RDB 文件結構
- 重點回顧
- AOF 持久化
- AOF 持久化的實現
- 重點回顧
- 事件
- 文件事件
- 重點回顧
- 參考資料
- 客戶端
- 客戶端屬性
- 重點回顧
- 服務器
- 命令請求的執行過程
- 重點回顧
- 第三部分:多機數據庫的實現
- 復制
- 舊版復制功能的實現
- 重點回顧
- Sentinel
- 啟動并初始化 Sentinel
- 重點回顧
- 參考資料
- 集群
- 節點
- 重點回顧
- 第四部分:獨立功能的實現
- 發布與訂閱
- 頻道的訂閱與退訂
- 重點回顧
- 參考資料
- 事務
- 事務的實現
- 重點回顧
- Lua 腳本
- 創建并修改 Lua 環境
- 重點回顧
- 排序
- SORT <key> 命令的實現
- 重點回顧
- 二進制位數組
- GETBIT 命令的實現
- 重點回顧
- 慢查詢日志
- 慢查詢記錄的保存
- 慢查詢日志的閱覽和刪除
- 添加新日志
- 重點回顧
- 監視器
- 成為監視器
- 向監視器發送命令信息
- 重點回顧
- 源碼、相關資源和勘誤