Redis 常见数据结构(string、list、set、zset 等)及底层实现?

1 个回答

  • 张三丰
    慢慢理解世界,慢慢更新自己。
    ## 1. String(字符串) * **存储内容**:二进制安全,既能存文本也能存序列化后的对象,最大 512MB。 * **底层实现**: * **SDS(Simple Dynamic String)** 动态字符串结构: * 包含 `len`(长度)、`alloc`(已分配空间)、`buf[]`(实际数据) * 预分配机制,减少内存重分配 * 二进制安全,不依赖 `\0` 结尾 * **适用场景**: * 缓存对象、计数器、分布式锁 * **常用命令**: ```shell SET key value GET key INCR key ``` ## 2. List(列表) * **存储内容**:按插入顺序排序,可重复,支持头尾插入和范围查询。 * **底层实现**: * 早期:**ziplist(压缩列表)**(元素少且短时) * 元素多时:**linkedlist(双向链表)** * Redis 3.2+:统一为 **quicklist**(多个 ziplist 节点组成的双向链表) * 节省内存(ziplist 压缩)+ 快速插入(链表特性) * **适用场景**: * 消息队列、任务列表、时间轴 * **常用命令**: ```shell LPUSH key value RPUSH key value LPOP key ``` ## 3. Hash(哈希) * **存储内容**:键值对集合,类似 `Map<String, String>`。 * **底层实现**: * **ziplist(压缩列表)**:字段少且短 * **hashtable(哈希表)**:字段多时 * **适用场景**: * 存储对象属性(用户信息、配置项) * **常用命令**: ```shell HSET user:1 name Tom HGET user:1 name HGETALL user:1 ``` ## 4. Set(集合) * **存储内容**:无序、唯一的元素。 * **底层实现**: * **intset(整数集合)**:全是整数且元素少 * **hashtable**:存储更多或非整数元素 * **适用场景**: * 去重、交集/并集计算 * **常用命令**: ```shell SADD key value SMEMBERS key SINTER key1 key2 ``` ## 5. ZSet(有序集合) * **存储内容**:每个元素关联一个分数(score),按分数排序,分数可重复但元素唯一。 * **底层实现**: * **ziplist**:数据量小 * **skiplist(跳表)+ dict(哈希表)**: * 哈希表:O(1) 查找元素 * 跳表:O(logN) 按 score 范围查找 * 跳表支持范围扫描、排名操作,比红黑树实现更简单且性能可控 * **适用场景**: * 排行榜、延时任务 * **常用命令**: ```shell ZADD key score member ZRANGE key 0 10 WITHSCORES ZREVRANK key member ``` ## 6. 其他特殊结构 ### (1) Bitmap(位图) * 基于 String 按位存储,适合状态标记、签到记录。 * 底层是二进制操作,没有独立结构。 ### (2) HyperLogLog * 基于概率算法的基数统计,误差 0.81%,内存恒定 12KB。 * 适合 UV 统计。 ### (3) GEO * 基于 ZSet 实现(score 存 geohash),支持地理位置存储和范围查询。 ## 7. 底层编码选择逻辑 * Redis 会根据 **数据量大小** 和 **元素特性** 在不同编码间自动切换: * ziplist → linkedlist / hashtable / skiplist * intset → hashtable * 可以用命令查看: ```shell OBJECT ENCODING key ```
    发布于 2025-08-12 16:46 •IP属地 安徽
    举报
    评论
    收藏