Redis与MySQL回写中的数据类型存储设计

一、前置

在 Redis 与 MySQL 数据回写场景中,Redis 核心定位是缓存 / 高效存储层,MySQL 是持久化存储层,数据回写通常是「Redis 更新→同步 / 异步更新 MySQL」或「MySQL 更新→刷新 Redis」。KV 设计需遵循 3 个通用原则:

  1. 键名(Key):采用「命名空间:业务模块:关联主键:标识」格式,小写 + 下划线,保证唯一性、可读性、可扩展性(如app:user:id:1001)。

  2. 值(Value):优先简化存储(如主键 ID),需完整数据时用 JSON 序列化,避免冗余,方便回写解析。

  3. 回写优先级:修改操作先保证 MySQL 数据一致性(持久化),再刷新 Redis;高频读写场景可先操作 Redis(原子操作),再异步回写 MySQL(需加日志兜底,防止数据丢失)。

二、数据类型

1、String(字符串)- 单值单键,基础通用

01. 类型特性

Redis 最基础的数据类型,二进制安全,可存储字符串、数字、JSON 序列化对象,最大 512MB,支持原子自增 / 自减、过期时间设置。

02. 适合的 MySQL 场景

  • 单条记录的单个字段(如用户昵称、商品价格、订单状态)。
  • 单条记录的完整序列化对象(如单条用户详情、单条商品信息,适合整行查询场景)。
  • 全局 / 单对象计数器(如商品库存、订单号自增、文章阅读量,对应 MySQL 的 INT/BIGINT 计数器字段)。

03.KV 设计规范

04.优缺点

  • 优点:简单易用、查询高效、支持过期时间、适配大部分基础场景。
  • 缺点:存储完整对象时,修改单个字段需反序列化 + 序列化,效率较低;计数器场景需注意异步回写的兜底方案。

2、Hash(哈希)- 单键多字段,适配单行记录

01. 类型特性

一个 Key 对应一个「field-value」集合,类似 MySQL 的单行记录,field 对应表字段,value 对应字段值,支持单个 field 的新增 / 修改 / 查询。

02. 适合的 MySQL 场景

  • 单条记录的多个字段(如用户资料、商品详情),适合频繁修改单个字段的场景。
  • 替代 String 存储完整对象,解决「修改单个字段低效」的问题。
  • 不适合存储多条记录(多条记录推荐 List/Set/ZSet)。

03. KV 设计规范

  • 键名(Key):命名空间:业务模块:主键名:主键值(对应 MySQL 单条记录,主键唯一)。
  • 字段名(Field):直接对应 MySQL 表的字段名 (保持一致,方便解析和回写,如usernameage)。
  • 字段值(Value):对应 MySQL 字段原值,数字存数值型,日期存 ISO 格式字符串,无需序列化。

04.回写注意:

  1. 单个字段修改:直接提取「Key 中的主键 1001」「Field 对应的字段名 age」「新值 26」,执行UPDATE user SET age=26 WHERE id=1001;,无需反序列化,效率极高。
  2. 多个字段修改:通过HGETALL获取所有 field-value,组装 UPDATE 语句回写 MySQL,避免多次数据库操作。
  3. 过期时间:Hash 本身不支持直接设置过期,需给对应的 Key 设置过期(如EXPIRE app:user:id:1001 7200)。

05.优缺点

  • 优点:修改单个字段高效、节省空间(无需 JSON 序列化)、可读性强、适配单行记录的高频更新场景。
  • 缺点:不支持存储多条记录、不支持复杂查询条件(如 MySQL 的多条件 WHERE 筛选)、无天然排序功能。

3、List(列表)- 有序可重复,适配队列 / 最新列表

01. 类型特性

有序集合(按插入顺序排序),可重复,支持两端插入(LPUSH/RPUSH)、两端删除(LPOP/RPOP)、裁剪(LTRIM),底层是双向链表。

02. 适合的 MySQL 场景

  • 有序的多条记录集合(按时间 / 插入顺序排序),如用户最近浏览记录、文章评论列表、待处理订单队列。
  • 对应 MySQL 的「SELECT * FROM 表 WHERE 条件 ORDER BY 排序字段 LIMIT N」查询结果。

03. KV 设计规范

  • 键名(Key):命名空间:业务模块:关联主键名:关联主键值:列表标识(如用户浏览记录、待处理订单队列)。
  • 列表元素(Value):
    1. 简化版(推荐):存储 MySQL 记录的主键值(如商品 id、订单 id),节省 Redis 存储空间,回写 / 查询时通过主键从 MySQL/Redis Hash 中获取完整记录。
    2. 完整版:存储 JSON 序列化字符串(完整记录),适合数据量小、无需二次查询的场景。
  • 排序控制:LPUSH(从左侧插入,最新记录在前)、RPUSH(从右侧插入,最早记录在前),对应 MySQL 的ORDER BY 字段 DESC/ASC

04.优缺点

  • 优点:有序、支持双向操作、适合实现队列 / 最新列表、裁剪操作可控制数据量。
  • 缺点:查询中间元素效率低、不支持去重、数据量过大时维护成本高。

4、Set(集合)- 无序不可重复,适配去重 / 集合运算

01. 类型特性

无序集合,元素不可重复,支持交集(SINTER)、并集(SUNION)、差集(SDIFF)等高效集合运算,适合去重和关联查询。

02. 适合的 MySQL 场景

  • 去重的多条记录集合,如用户关注列表、商品标签集合、中奖用户名单(避免重复中奖)。
  • 对应 MySQL 的「DISTINCT查询」或「多表关联的交集 / 并集查询」(如共同关注、共同收藏)。

03. KV 设计规范

  • 键名(Key):命名空间:业务模块:关联主键名:关联主键值:集合标识(如用户关注列表、商品标签集合)。
  • 集合元素(Value):
    1. 简化版(推荐):存储 MySQL 记录的主键值(如关注的用户 id、标签 id),方便集合运算。
    2. 完整版:存储 JSON 序列化字符串,适合数据量小、无需集合运算的去重场景。
  • 去重规则:Set 天然去重,插入重复元素会被忽略,对应 MySQL 的UNIQUE约束。

04.优缺点

  • 优点:天然去重、支持高效集合运算、查询元素是否存在(SISMEMBER)效率高。
  • 缺点:无序、不支持排序、不支持存储额外字段(如关注时间)。

5、Sorted Set(ZSet,有序集合)- 有序不可重复,适配榜单 / 延时队列

01. 类型特性

有序集合,元素不可重复,每个元素对应一个「分数(score)」,按分数排序(升序 / 降序),支持排名查询、分数更新。

02. 适合的 MySQL 场景

  • 按权重排序的去重记录集合,如商品销量排行榜、用户积分排名、热门文章榜单、延时队列。
  • 对应 MySQL 的「SELECT * FROM 表 ORDER BY 权重字段 DESC/ASC LIMIT N」查询结果。

03. KV 设计规范

  • 键名(Key):命名空间:业务模块:榜单标识:排序字段(如商品销量榜、用户积分榜)。
  • 有序集合元素(Member):存储 MySQL 记录的主键值(如商品 id、用户 id),节省空间。
  • 分数(Score):对应 MySQL 的权重字段值(如销量、积分、时间戳),支持数值型,用于排序。
  • 排序规则:ZREVRANGE(按分数降序,对应榜单从高到低)、ZRANGE(按分数升序,对应延时队列)。

04. 优缺点

  • 优点:有序去重、支持权重排序、查询排名高效、适配榜单 / 延时队列场景。
  • 缺点:修改 score 需重新插入、数据量过大时排序维护成本高、不支持复杂权重计算。

6、Bitmap(位图)- 高效统计布尔值

  • 特性:基于 String 实现,按位存储(0/1),1MB 可存储 800 多万条布尔值,适合海量布尔数据统计。
  • MySQL 场景 :用户签到、是否已读、海量用户激活状态(对应 MySQL 的is_signis_read等布尔字段表)。
  • KV 设计
    • Key:命名空间:业务模块:关联主键:统计维度(如app:sign:user_id:1001:202602)。
    • Offset:对应统计维度主键(如签到日期→当月天数 - 1)。
    • Bit 值:1 = 是,0 = 否。
  • 回写注意:先设置 Bitmap,再回写 MySQL 布尔字段;统计结果(如总签到天数)可定期回写 MySQL 统计报表。

7、HyperLogLog(HLL)- 海量数据近似去重

  • 特性:固定占用 12KB,支持海量数据基数(不重复元素个数)统计,误差率约 0.81%,不存储具体元素。
  • MySQL 场景 :网站 UV、商品独立浏览用户数(对应 MySQL 的COUNT(DISTINCT user_id),海量数据时查询低效)。
  • KV 设计
    • Key:命名空间:业务模块:统计维度:时间(如app:access:uv:20260205)。
    • 元素:存储 MySQL 记录的唯一标识(如 user_id)。
  • 回写注意:无法从 HLL 回写具体 MySQL 记录,仅可将统计结果回写 MySQL 统计报表;原始数据仍需写入 MySQL。

8、Geo(地理空间)- LBS 场景适配

  • 特性:存储地理坐标(纬度 / 经度),支持距离计算、附近地点查询,底层基于 ZSet。
  • MySQL 场景 :门店、外卖商家、用户位置(对应 MySQL 的latlng字段表)。
  • KV 设计
    • Key:命名空间:业务模块:地理数据标识(如app:store:geo_list)。
    • Member:门店 / 商家 id。
    • 坐标:纬度在前,经度在后,对应 MySQL 的latlng
  • 回写注意 :先更新 MySQL 坐标字段,再用GEOADD刷新 Redis Geo;查询结果仅获取主键,无需回写 Redis。

三、各 Redis 数据类型针对性设置

1、String

配置项 具体内容
适配 MySQL 场景 1. 单条记录的单个字段(如用户名、商品价格) 2. 单条记录完整序列化对象(如用户详情) 3. 全局 / 单对象计数器(如库存、阅读量)
KV 设计规范 - Key: 单个字段:命名空间:业务模块:主键名:主键值:字段名(如app:user:id:1001:username) 完整对象:命名空间:业务模块:主键名:主键值(如app:user:id:1001) 计数器:命名空间:业务模块:主键名:主键值:计数器(如app:goods:id:2001:stock) - Value: 单个字段 / 计数器:MySQL 字段原值(无需序列化) 完整对象:JSON 序列化字符串(对应 MySQL 整行记录)
回写核心配置 1. 单个字段 :从 Key 提取主键 + 字段名,从 Value 提取新值,直接组装UPDATE 表 SET 字段=新值 WHERE 主键=值回写 2. 完整对象:反序列化 JSON 获取所有字段,组装 UPDATE 语句回写;新增记录先写 MySQL 获取自增主键,再序列化写入 Redis 3. 计数器:Redis 原子操作(INCR/DECRBY)后,异步队列兜底回写 MySQL 对应数字字段,失败则记录日志重试
典型 Redis 操作 SET(带过期)、GET、INCR、DECRBY

2、Hash

| 配置项 | 具体内容 |
| 适配 MySQL 场景 | 单条记录的多个字段(如用户资料、商品详情),适合频繁修改单个字段的场景,替代 String 解决完整对象修改低效问题 |
| KV 设计规范 | - Key:命名空间:业务模块:主键名:主键值(对应 MySQL 单条记录,如app:user:id:1001) - Field:直接对应 MySQL 表的字段名(如usernameage),保持一致方便解析 - Value:MySQL 字段原值(数字存数值、日期存 ISO 字符串,无需序列化) |
| 回写核心配置 | 1. 单个字段修改:从 Key 提取主键,从 Field 提取字段名,从 Value 提取新值,直接单字段 UPDATE 回写,无需反序列化,效率极高 2. 多字段修改:HGETALL 获取所有 field-value,组装批量 UPDATE 语句回写,减少 MySQL 连接次数 3. 给 Key 单独配置过期时间(Hash 本身不支持直接过期) |

典型 Redis 操作 HMSET(批量写入)、HSET(单字段修改)、HGET(单字段查询)、HGETALL(全字段查询)、EXPIRE(设置过期)

3、List

| 配置项 | 具体内容 |
| 适配 MySQL 场景 | 有序的多条记录集合(按时间 / 插入顺序排序),如: 1. 用户最近浏览记录 2. 待处理订单队列 3. 文章评论列表(按时间排序) |
| KV 设计规范 | - Key:命名空间:业务模块:关联主键名:关联主键值:列表标识(如app:browse:user_id:1001:latest_list) - Value(列表元素): 推荐:MySQL 记录主键 ID(如商品 id、订单 id),节省内存 - 排序:LPUSH(最新在前,对应 MySQL DESC)、RPUSH(最早在前,对应 MySQL ASC),LTRIM 裁剪保留前 N 条(避免过长) |
| 回写核心配置 | 1. 缓存列表(如浏览记录):List 是 MySQL 查询结果缓存,不直接回写;新增记录时先写 MySQL 原始表,再插入 Redis List 2. 队列场景(如待处理订单):RPUSH 入队→LPOP 出队处理→处理完成后 UPDATE MySQL 订单状态→处理失败则重新 RPUSH 入队兜底 3. 完整版(JSON 元素):修改元素时先反序列化提取 MySQL 主键,再针对性回写对应记录 |

典型 Redis 操作 LPUSH/RPUSH(插入)、LPOP/RPOP(删除)、LRANGE(查询列表)、LTRIM(裁剪)

4、Set

| 配置项 | 具体内容 |
| 适配 MySQL 场景 | 需去重的多条记录集合,如: 1. 用户关注 / 粉丝列表(避免重复关注) 2. 商品标签集合 3. 多表关联交集 / 并集查询(如共同关注) |
| KV 设计规范 | - Key:命名空间:业务模块:关联主键名:关联主键值:集合标识(如app:follow:user_id:1001:follow_list) - Value(集合元素):推荐存储 MySQL 记录主键 ID(如关注用户 id、标签 id),方便高效进行集合运算(SINTER/SUNION) - 去重:依赖 Set 天然去重特性,对应 MySQL 表的 UNIQUE 约束兜底 |
| 回写核心配置 | 1. 新增元素:先 SADD 插入 Redis Set,再 INSERT MySQL 表(依赖 UNIQUE 约束避免重复) 2. 删除元素:先 SREM 删除 Redis 元素,再 DELETE MySQL 对应记录 3. 集合运算结果:仅获取主键集合,无需回写 Redis,详情从 MySQL/Redis Hash 查询 |

典型 Redis 操作 SADD(新增)、SREM(删除)、SISMEMBER(判断存在)、SINTER(交集)、SUNION(并集)

5、ZSet

| 配置项 | 具体内容 |
| 适配 MySQL 场景 | 需按权重排序的去重记录集合,如: 1. 商品销量 / 积分排行榜 2. 用户等级排名 3. 延时任务队列(按时间戳排序) |
| KV 设计规范 | - Key:命名空间:业务模块:榜单标识:排序字段(如app:goods:rank:sales_desc) - Member:MySQL 记录主键 ID(如商品 id、用户 id) - Score:对应 MySQL 权重字段值(如销量、积分、时间戳),用于排序,支持更新覆盖 |
| 回写核心配置 | 1. 实时更新场景:先 UPDATE MySQL 权重字段,再 ZADD 刷新 Redis Score(覆盖更新) 2. 高频榜单场景:定时从 MySQL 查询前 N 条记录,批量 ZADD 更新 Redis,避免实时更新压力过大 3. 延时队列:Score 设为执行时间戳,查询已到期元素处理,完成后 UPDATE MySQL 状态,失败则重新设置 Score 入队 |

典型 Redis 操作 ZADD(新增 / 更新 Score)、ZREVRANGE(降序查询榜单)、ZRANGE(升序查询)、ZREM(删除元素)

6、特殊数据类型

数据类型 适配 MySQL 场景 KV 设计规范 回写核心配置
Bitmap(位图) 海量布尔值统计(用户签到、是否已读) Key:命名空间:业务模块:关联主键:统计维度(如app:sign:user_id:1001:202602)Offset:统计维度主键(如当月天数 - 1)Bit 值:1 = 是、0 = 否 先设置 Bitmap,再回写 MySQL 布尔字段;统计结果(如总签到天数)定期回写 MySQL 统计报表
HyperLogLog(HLL) 海量数据近似去重(网站 UV、独立访客) Key:命名空间:业务模块:统计维度:时间(如app:access:uv:20260205)元素:MySQL 记录唯一标识(如 user_id) 无法回写具体记录,仅将统计结果回写 MySQL 统计报表;原始数据需单独写入 MySQL
Geo(地理空间) LBS 场景(门店、外卖商家位置) Key:命名空间:业务模块:地理数据标识(如app:store:geo_list)Member:门店 / 商家 id坐标:对应 MySQL lat(纬度)、lng(经度) 先更新 MySQL 坐标字段,再 GEOADD 刷新 Redis;查询结果仅获取主键,无需回写 Redis
相关推荐
小陈工7 小时前
Python Web开发入门(十七):Vue.js与Python后端集成——让前后端真正“握手言和“
开发语言·前端·javascript·数据库·vue.js·人工智能·python
0xDevNull11 小时前
MySQL数据冷热分离详解
后端·mysql
科技小花11 小时前
数据治理平台架构演进观察:AI原生设计如何重构企业数据管理范式
数据库·重构·架构·数据治理·ai-native·ai原生
一江寒逸11 小时前
零基础从入门到精通MySQL(中篇):进阶篇——吃透多表查询、事务核心与高级特性,搞定复杂业务SQL
数据库·sql·mysql
D4c-lovetrain11 小时前
linux个人心得22 (mysql)
数据库·mysql
阿里小阿希12 小时前
CentOS7 PostgreSQL 9.2 升级到 15 完整教程
数据库·postgresql
荒川之神12 小时前
Oracle 数据仓库雪花模型设计(完整实战方案)
数据库·数据仓库·oracle
做个文艺程序员12 小时前
MySQL安全加固十大硬核操作
数据库·mysql·安全
不吃香菜学java12 小时前
Redis简单应用
数据库·spring boot·tomcat·maven
一个天蝎座 白勺 程序猿12 小时前
Apache IoTDB(15):IoTDB查询写回(INTO子句)深度解析——从语法到实战的ETL全链路指南
数据库·apache·etl·iotdb