摘要
- 本文介绍 Redis Set 数据类型
- 本文基于
redis-7.4.7,springboot-3.5.8 - Redis官网:https://redis.io/
- Redis 命令文档:https://redis.io/docs/latest/commands/
Set 核心详解
- Redis Set 是一个无序、不重复元素集合,本质上是:
bash
key -> Set<String>
# 说明
元素唯一(自动去重)
无顺序(不保证插入顺序)
元素类型为 String(二进制安全)
-
Set 的核心特性
自动去重
高效成员判断
支持集合运算
操作原子性强 -
Redis Set 的理论最大长度为 2^32 - 1 = 4294967295,但实际业务中,元素数量 ≥ 10,000 就算 BigKey 了。
-
Set 应用场景
bash
# 微信抽奖小程序
1)点击参与抽奖加入集合
SADD key {userlD}
2)查看参与抽奖所有用户
SMEMBERS key
3)抽取count名中奖者
SRANDMEMBER key [count] / SPOP key [count]
# 微信微博点赞,收藏,标签
1) 点赞
SADD like:{消息ID} {用户ID}
2) 取消点赞
SREM like:{消息ID} {用户ID}
3) 检查用户是否点过赞
SISMEMBER like:{消息ID} {用户ID}
4) 获取点赞的用户列表
SMEMBERS like:{消息ID}
5) 获取点赞用户数
SCARD like:{消息ID}
# 集合操作
# 交集:多个集合中同时存在的元素
SINTER set1 set2 set3 -> { c } # 交集,共同关注 / 共同好友 / 共同兴趣
# 并集:存在于任意一个集合中的元素
SUNION set1 set2 set3 -> { a,b,c,d,e } # 多来源合并后的用户全集
# 差集:只存在于第一个集合中的元素
SDIFF set1 set2 set3 -> {a} # 差集,推荐好友
-
生产环境建议
Set 适合 成员资格判断
始终控制成员规模
大 Set 遍历使用 SSCAN
集合运算放在离线或低频场景
删除大 Set 使用 UNLINK
Set 命令
- SpringBoot 的
RedisTemplate<K,V>.opsForSet()中 Set 数据类型 的操作方法与 Redis 原生命令的对应关系如下:
写操作(增 / 删 / 移动)
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 向集合添加元素 | add(K key, V... values) |
SADD key member [member ...] |
返回新增成员数量 |
移除 / 弹出成员
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 从集合移除元素 | remove(K key, Object... values) |
SREM key member [member ...] |
返回移除成员数量 |
| 随机弹出一个元素 | pop(K key) |
SPOP key |
随机且删除 |
| 随机弹出多个元素 | pop(K key, long count) |
SPOP key count |
Redis ≥ 3.2 |
成员移动(原子)
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 将成员移动到其他集合 | move(K key, V value, K destKey) |
SMOVE source dest member |
原子操作 |
集合大小
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 获取集合大小 | size(K key) |
SCARD key |
--- |
成员存在性判断
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 判断是否是成员 | isMember(K key, Object o) |
SISMEMBER key member |
--- |
| 批量判断成员是否存在 | isMember(K key, Object... objects) |
SMISMEMBER key member [member ...] |
Redis ≥ 6.2 |
交集(Intersection)
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 计算交集 | intersect(K key, K otherKey) |
SINTER key key |
O(N × M) |
| 计算交集 | intersect(K key, Collection<K> otherKeys) |
SINTER key [key ...] |
--- |
| 计算交集 | intersect(Collection<K> keys) |
SINTER key [key ...] |
--- |
| 交集并存储 | intersectAndStore(K key, K otherKey, K destKey) |
SINTERSTORE dest key key |
返回结果数量 |
| 交集并存储 | intersectAndStore(K key, Collection<K> otherKeys, K destKey) |
SINTERSTORE dest key [key ...] |
--- |
| 交集并存储 | intersectAndStore(Collection<K> keys, K destKey) |
SINTERSTORE dest key [key ...] |
--- |
并集(Union)
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 计算并集 | union(K key, K otherKey) |
SUNION key key |
--- |
| 计算并集 | union(K key, Collection<K> otherKeys) |
SUNION key [key ...] |
--- |
| 计算并集 | union(Collection<K> keys) |
SUNION key [key ...] |
--- |
| 并集并存储 | unionAndStore(K key, K otherKey, K destKey) |
SUNIONSTORE dest key key |
--- |
| 并集并存储 | unionAndStore(K key, Collection<K> otherKeys, K destKey) |
SUNIONSTORE dest key [key ...] |
--- |
| 并集并存储 | unionAndStore(Collection<K> keys, K destKey) |
SUNIONSTORE dest key [key ...] |
--- |
差集(Difference)
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 计算差集 | difference(K key, K otherKey) |
SDIFF key key |
key 顺序影响结果 |
| 计算差集 | difference(K key, Collection<K> otherKeys) |
SDIFF key [key ...] |
--- |
| 计算差集 | difference(Collection<K> keys) |
SDIFF key [key ...] |
--- |
| 差集并存储 | differenceAndStore(K key, K otherKey, K destKey) |
SDIFFSTORE dest key key |
--- |
| 差集并存储 | differenceAndStore(K key, Collection<K> otherKeys, K destKey) |
SDIFFSTORE dest key [key ...] |
--- |
| 差集并存储 | differenceAndStore(Collection<K> keys, K destKey) |
SDIFFSTORE dest key [key ...] |
--- |
全量 / 随机读取
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 获取所有成员 | members(K key) |
SMEMBERS key |
大集合慎用 |
| 随机获取一个成员 | randomMember(K key) |
SRANDMEMBER key |
不删除 |
| 随机获取不重复成员 | distinctRandomMembers(K key, long count) |
SRANDMEMBER key count |
count > 0 |
| 随机获取可重复成员 | randomMembers(K key, long count) |
SRANDMEMBER key -count |
count < 0 |
游标扫描(大集合推荐)
| 方法功能 | 方法 | Redis 原始命令 | 备注 |
|---|---|---|---|
| 游标扫描成员 | scan(K key, ScanOptions options) |
SSCAN key cursor [MATCH] [COUNT] |
推荐替代 SMEMBERS |