
Redis 新手入门从命令行掌握 String、Hash、List、Set、ZSet 和常用操作最近在命令行里学习 Redis整理一下 Redis 的基础数据结构、常用命令以及后续需要继续掌握的进阶内容。Redis 是一个基于内存的 key-value 数据库。它不像 MySQL 那样需要提前建库建表而是通过不同命令直接创建不同类型的数据。比如SET name zhangsan # 创建 String HSET user:1 name zhangsan # 创建 Hash LPUSH mylist a # 创建 List SADD myset java # 创建 Set ZADD rank 100 zhangsan # 创建 ZSetRedis 里每个 key 都有自己的类型。同一个 key 不能既是 String又是 Hash。如果类型用错会报WRONGTYPE Operation against a key holding the wrong kind of value一、StringRedisTemplate 和 Redisson 是什么区别在 Java 项目里操作 Redis经常会看到两个工具StringRedisTemplate和Redisson。1. StringRedisTemplateStringRedisTemplate是 Spring Data Redis 提供的 Redis 操作模板。它更像是 Redis 命令的 Java 封装。例如stringRedisTemplate.opsForValue().set(user:1,zhangsan);StringvaluestringRedisTemplate.opsForValue().get(user:1);对应 Redis 命令SET user:1 zhangsan GET user:1它适合做基础 Redis 操作比如缓存 验证码 token 计数器 Hash/List/Set/ZSet 操作2. RedissonRedisson 是一个基于 Redis 的分布式工具框架。它不只是操作 Redis 数据还封装了很多分布式能力例如分布式锁 延迟队列 布隆过滤器 分布式信号量 分布式限流比如分布式锁RLocklockredissonClient.getLock(coupon:stock:1001);lock.lock();try{// 执行业务逻辑}finally{lock.unlock();}表面上是 Java 的lock.lock()底层其实是 Redisson 用 Redis 帮我们实现了分布式锁。3. 简单总结StringRedisTemplate直接操作 Redis 数据结构。 Redisson把 Redis 封装成分布式工具。常见选择普通缓存读写StringRedisTemplate 分布式锁、延迟队列、限流Redisson它们不是互相替代的关系真实项目里经常一起使用。二、String 类型和 incr 自增Redis 的 String 类型可以存普通文本也可以存数字字符串。例如SET count 10 GET count如果 value 是整数形式的字符串就可以执行自增INCR count INCRBY count 5执行后GET count结果会变成16Java 中LongvalueredisTemplate.opsForValue().increment(count,1);底层对应的就是 Redis 的INCRBY命令。但是注意如果 value 不是整数不能自增。例如SET name zhangsan INCR name会报错ERR value is not an integer or out of range下面这些不能自增abc zhangsan 1.5 {\count\:1}下面这些可以自增1 100 -5 0还有一个特殊情况如果 key 不存在Redis 会把它当成 0然后执行自增。DEL count INCR count GET count结果1三、如何查看当前 Redis 里有哪些 key1. KEYS 命令本地学习时可以用KEYS *查看当前库中所有 key。例如KEYS *可能返回1) mylist 2) myzset 3) mykey 4) myhash 5) myset但是KEYS *会一次性扫描所有 key。数据量很大时可能阻塞 Redis所以生产环境不推荐使用。2. SCAN 命令更推荐使用SCAN 0 MATCH * COUNT 100例如SCAN 0 MATCH * COUNT 100返回1) 0 2) 1) mylist 2) myzset 3) mykey 4) myhash 5) myset这个结果分成两部分第一部分0 是下一次扫描用的游标 cursor。 第二部分本次扫描出来的 key 列表。如果返回的 cursor 是0说明扫描结束了。如果返回的 cursor 不是 0比如1) 384 2) 1) user:1 2) user:2说明还没有扫描完下一次需要继续SCAN 384 MATCH * COUNT 100直到某次返回的游标是0才表示扫描完成。可以把SCAN理解成分页查询第一行下一页页码 第二行这一页查到的 key四、查看 key 的类型和值Redis 里不同类型的 key要用不同命令查看。先查看类型TYPE key例如TYPE mylist TYPE myhash TYPE myset TYPE myzset根据类型选择查看命令GET key # String HGETALL key # Hash LRANGE key 0 -1 # List SMEMBERS key # Set ZRANGE key 0 -1 WITHSCORES # ZSet从小到大 ZREVRANGE key 0 -1 WITHSCORES # ZSet从大到小五、Hash适合存对象Hash 类似 Java 里的MapString, String适合存对象的多个字段。创建 HashHSET user:1 name zhangsan age 18 city nanjing查看整个 HashHGETALL user:1查看某个字段HGET user:1 name修改字段HSET user:1 age 20删除字段HDEL user:1 city查看所有字段名HKEYS user:1查看所有字段值HVALS user:1可以理解成user:1{name:zhangsan,age:18,city:nanjing}适合存用户信息 商品信息 优惠券信息 配置项六、List有顺序的列表List 是有序列表可以从左边插入也可以从右边插入。从左边插入LPUSH mylist a LPUSH mylist b LPUSH mylist c此时列表大概是c b a查看整个 ListLRANGE mylist 0 -1从右边插入RPUSH mylist d RPUSH mylist e查看LRANGE mylist 0 -1弹出左边元素LPOP mylist弹出右边元素RPOP mylist查看长度LLEN mylist按下标查看LINDEX mylist 0List 适合消息队列雏形 最近浏览记录 任务列表 时间线七、Set无序去重集合Set 是无序、不重复集合。创建 SetSADD myset java SADD myset redis SADD myset mysql SADD myset java虽然java添加了两次但是 Set 里只会保留一份。查看所有成员SMEMBERS myset判断元素是否存在SISMEMBER myset java删除元素SREM myset mysql查看数量SCARD mysetSet 还支持集合运算。交集SINTER set1 set2并集SUNION set1 set2差集SDIFF set1 set2Set 适合去重 标签 黑名单 白名单 共同关注 抽奖名单八、ZSet有序集合ZSet 也叫 Sorted Set有序集合。它和 Set 一样成员不重复但是每个成员都有一个分数scoreRedis 根据 score 排序。创建排行榜ZADD rank 100 zhangsan ZADD rank 90 lisi ZADD rank 120 wangwu查看从小到大排序ZRANGE rank 0 -1 WITHSCORES结果类似lisi 90 zhangsan 100 wangwu 120查看从大到小排序ZREVRANGE rank 0 -1 WITHSCORES查看某个成员分数ZSCORE rank zhangsan增加某个成员分数ZINCRBY rank 10 zhangsan查看排名从小到大ZRANK rank zhangsan查看排名从大到小ZREVRANK rank zhangsan删除成员ZREM rank lisiZSet 适合排行榜 热搜榜 积分榜 按时间排序的数据 延迟任务九、给 key 设置过期时间Redis 的 key 可以设置过期时间到期后自动删除。1. 设置过期时间先创建 keySET name zhangsan设置 60 秒后过期EXPIRE name 602. 创建时直接设置过期单位是秒SET code 123456 EX 60单位是毫秒SET code 123456 PX 600003. 查看剩余过期时间TTL name返回值含义正数还剩多少秒过期 -1key 存在但是没有设置过期时间 -2key 不存在毫秒级查看PTTL name4. 延长过期时间重新设置过期时间即可EXPIRE name 300注意这不是在原来的基础上增加 300 秒而是从当前时刻开始重新设置为 300 秒。5. 取消过期时间PERSIST name取消后TTL name会返回-1表示 key 存在但没有过期时间。十、Redis 新手必须掌握的通用命令1. key 相关KEYS * SCAN 0 MATCH * COUNT 100 EXISTS key DEL key TYPE key RENAME oldkey newkey EXPIRE key 60 TTL key PERSIST key其中最重要的是TYPE key因为只有知道 key 的类型才知道应该用什么命令查看它。2. 数据库切换Redis 默认有多个库编号从 0 开始。查看当前库KEYS *切换到 1 号库SELECT 1切回 0 号库SELECT 0查看当前库 key 数量DBSIZE清空当前库FLUSHDB清空所有库FLUSHALL注意FLUSHDB FLUSHALL这两个命令很危险本地学习可以用生产环境不要乱敲。3. 查看 Redis 信息查看全部信息INFO查看内存信息INFO memory查看客户端连接INFO clients查看持久化信息INFO persistence4. 慢查询查看慢查询日志SLOWLOG GET查看最近 10 条SLOWLOG GET 10查看慢查询数量SLOWLOG LEN十一、后续要学的进阶内容目前先掌握 String、Hash、List、Set、ZSet、过期时间、SCAN、TYPE、DEL 等基础操作即可。后续可以继续学习下面这些内容。1. Redis 事务Redis 事务主要命令是MULTI 命令1 命令2 命令3 EXEC例如MULTI SET a 1 SET b 2 INCR count EXEC从MULTI开始命令不会立刻执行而是先进入队列。直到执行EXECRedis 才会把队列里的命令按顺序执行。如果想取消事务DISCARD需要注意的是Redis 事务和 MySQL 事务不完全一样。MySQL 事务强调要么全部成功要么全部失败可以回滚。Redis 事务更像把多个命令排队然后一次性按顺序执行。Redis 事务不支持 MySQL 那种复杂回滚。2. Lua 脚本Lua 脚本可以把多个 Redis 操作封装成一个原子操作。简单例子EVAL return redis.call(GET, KEYS[1]) 1 name意思是执行 Lua 脚本读取name这个 key。Lua 在 Redis 里很常见尤其适合处理这种场景判断库存是否足够 扣减库存 记录用户领取如果这几步分开执行可能出现并发问题。例如抢优惠券时逻辑可能是1. 判断库存是否大于 0 2. 判断用户是否领取过 3. 扣库存 4. 记录用户已领取这些操作如果拆开执行中间可能被其他请求插入。用 Lua 可以让这一组操作在 Redis 里一次性执行完保证原子性。所以后面做优惠券、秒杀、分布式锁时Lua 很重要。3. StreamStream 是 Redis 提供的消息流数据结构有点像 Redis 自带的消息队列。添加消息XADD mystream * user zhangsan action login查看消息XRANGE mystream - 读取消息XREAD COUNT 2 STREAMS mystream 0Stream 支持消息追加 消息读取 消费者组 消息确认 阻塞读取它适合做简单消息队列 日志流 异步任务 事件流但是在大型系统里专业消息队列一般还是会用 RocketMQ、Kafka、RabbitMQ 等。Redis Stream 可以理解为Redis 自带的轻量级消息队列能力。4. 持久化RDB 和 AOFRedis 是内存数据库数据主要存在内存里。但是如果服务器重启内存数据会丢失。为了避免数据完全丢失Redis 提供了持久化机制把数据保存到磁盘。主要有两种方式RDB AOFRDBRDB 是快照持久化。可以理解成隔一段时间给 Redis 当前数据拍一张照片保存到磁盘。优点文件紧凑 恢复速度较快 适合备份缺点如果 Redis 宕机可能丢失最近一次快照之后的数据。AOFAOF 是追加日志。可以理解成Redis 每执行一个写命令就把这个写命令记录到日志文件里。Redis 重启时可以重新执行这些写命令把数据恢复出来。优点数据更安全丢失更少。缺点文件通常比 RDB 大 恢复时可能比 RDB 慢简单记忆RDB拍照片。 AOF记账本。5. 淘汰策略Redis 数据存在内存里而内存是有限的。如果 Redis 内存满了该怎么办这就涉及 Redis 的淘汰策略。常见策略有noeviction不淘汰内存满了后写入直接报错。 allkeys-lru从所有 key 中淘汰最近最少使用的 key。 volatile-lru只从设置了过期时间的 key 中淘汰最近最少使用的 key。 allkeys-random从所有 key 中随机淘汰。 volatile-random从设置了过期时间的 key 中随机淘汰。 volatile-ttl优先淘汰快过期的 key。其中 LRU 可以简单理解成最近很少被访问的数据优先被删除。真实项目中如果 Redis 主要用来做缓存通常需要配置最大内存和合适的淘汰策略。否则内存满了之后可能导致 Redis 写入失败。6. 主从、哨兵、集群单机 Redis 有一个问题如果这一台 Redis 挂了服务就不可用了。所以生产环境通常不会只用单机 Redis而是会考虑高可用和扩展。主从复制主从复制就是一个主节点 master多个从节点 slave。主节点负责写从节点同步主节点的数据。常见用途读写分离 数据备份 提高读取能力但是主从模式有一个问题如果 master 挂了需要有人把 slave 提升为新的 master。这个过程如果手动做就不够自动化。哨兵 Sentinel哨兵就是用来监控 Redis 主从节点的。它可以监控 master 是否存活 发现 master 挂掉 自动选举新的 master 通知客户端新的 master 地址所以哨兵主要解决的是Redis 主从架构下的自动故障转移问题。Redis Cluster 集群Redis Cluster 是分片集群。它解决的不只是高可用还解决容量和性能扩展问题。简单理解数据被分散存储到多个 Redis 节点上。比如key1 在节点 A key2 在节点 B key3 在节点 C这样可以突破单机内存限制也能提高整体吞吐量。简单总结主从复制复制数据提高读能力。 哨兵监控主从自动故障转移。 Cluster数据分片支持更大规模。十二、Redis 新手学习路线建议按照下面顺序学习第一阶段基础数据结构String Hash List Set ZSet重点掌握SET / GET / INCR / INCRBY HSET / HGET / HGETALL LPUSH / RPUSH / LRANGE / LPOP / RPOP SADD / SMEMBERS / SISMEMBER / SINTER ZADD / ZRANGE / ZREVRANGE / ZINCRBY第二阶段key 通用操作查看 key 查看类型 删除 key 过期时间 扫描 key 切换数据库重点掌握KEYS * SCAN 0 MATCH * COUNT 100 TYPE key DEL key EXISTS key EXPIRE key seconds TTL key PERSIST key SELECT index DBSIZE第三阶段项目常用能力缓存 计数器 验证码 token 排行榜 分布式锁 延迟队列对应工具StringRedisTemplate基础 Redis 操作 Redisson分布式锁、延迟队列等高级工具第四阶段进阶能力事务 Lua Stream 持久化 淘汰策略 主从复制 哨兵 Cluster 集群十三、总结Redis 新手最重要的是先理解这几个点1. Redis 是 key-value 数据库。 2. 每个 key 都有自己的数据类型。 3. 不同数据类型要用不同命令操作。 4. Redis 不需要提前建表第一次写入时类型就确定了。 5. String、Hash、List、Set、ZSet 是最核心的五种基础数据结构。 6. key 可以设置过期时间适合做缓存、验证码、token。 7. 本地学习可以用 KEYS *生产环境更推荐 SCAN。 8. 后续做项目时普通缓存读写用 StringRedisTemplate分布式锁等高级能力可以用 Redisson。最简单的记忆方式String存简单值、JSON、计数器。 Hash存对象。 List存有序列表。 Set存去重集合。 ZSet存排行榜。 TTL/EXPIRE控制过期。 SCAN安全扫描 key。 TYPE判断 key 类型。学 Redis 不需要一开始就把所有高级概念都学完。先把基础命令练熟再结合 Java 项目里的缓存、分布式锁、优惠券库存、排行榜等场景去理解会更容易掌握。