Skip to content

basics

文件信息

  • 📄 原文件:01_basics.redis
  • 🔤 类型:Redis Commands

Redis 命令

redis
-- ============================================================
--                    Redis 基础教程
-- ============================================================
-- Redis: Remote Dictionary Server
-- 高性能的键值存储数据库,支持多种数据结构
-- ============================================================

-- ============================================================
--                    一、连接与基本操作
-- ============================================================

-- 连接 Redis(命令行)
-- redis-cli -h localhost -p 6379 -a password

-- 选择数据库(默认 0-15,共 16 个库)
SELECT 0

-- 查看当前数据库的 key 数量
DBSIZE

-- 清空当前数据库
FLUSHDB

-- 清空所有数据库
FLUSHALL

-- 查看服务器信息
INFO
INFO memory
INFO replication

-- ============================================================
--                    二、Key 操作
-- ============================================================

-- 设置键值
SET name "Redis"

-- 获取键值
GET name

-- 检查键是否存在
EXISTS name

-- 删除键
DEL name

-- 批量删除(使用通配符需要借助 SCAN)
-- 不推荐使用 KEYS *(会阻塞)

-- 设置过期时间(秒)
SET session "abc123"
EXPIRE session 3600

-- 设置过期时间(毫秒)
PEXPIRE session 3600000

-- 设置键值同时设置过期时间
SET token "xyz789" EX 3600
-- 或使用毫秒
SET token "xyz789" PX 3600000

-- 在指定时间点过期(Unix 时间戳)
EXPIREAT session 1735689600

-- 查看剩余生存时间(秒)
TTL session

-- 查看剩余生存时间(毫秒)
PTTL session

-- 移除过期时间(持久化)
PERSIST session

-- 重命名键
RENAME name newname
-- 仅当新键不存在时重命名
RENAMENX name newname

-- 查看键的类型
TYPE name

-- 序列化键值
DUMP name

-- 反序列化并恢复
RESTORE newkey 0 "\x00\x05Redis\t\x00..."

-- 移动键到其他数据库
MOVE name 1

-- 查找键(生产环境避免使用 KEYS *)
KEYS user:*
KEYS *name*

-- 使用 SCAN 迭代查找(推荐)
SCAN 0 MATCH user:* COUNT 100

-- 随机返回一个键
RANDOMKEY

-- ============================================================
--                    三、String(字符串)
-- ============================================================

-- String 是最基本的数据类型,可以存储字符串、整数、浮点数

-- 基本操作
SET greeting "Hello, Redis!"
GET greeting

-- 仅当键不存在时设置(常用于分布式锁)
SETNX lock:order "locked"

-- 仅当键存在时设置
SET name "NewValue" XX

-- 设置并返回旧值
GETSET counter 0

-- 同时设置多个键值
MSET user:1:name "Alice" user:1:age "25" user:1:city "Beijing"

-- 同时获取多个键值
MGET user:1:name user:1:age user:1:city

-- 仅当所有键都不存在时设置(原子操作)
MSETNX key1 "value1" key2 "value2"

-- 追加字符串
APPEND greeting " Welcome!"

-- 获取字符串长度
STRLEN greeting

-- 获取子字符串(0-based,包含两端)
GETRANGE greeting 0 4

-- 覆盖部分字符串
SETRANGE greeting 7 "World"

-- ============================================================
--                    四、数值操作
-- ============================================================

-- 设置数值
SET counter 100

-- 自增 1
INCR counter

-- 自减 1
DECR counter

-- 增加指定整数
INCRBY counter 10

-- 减少指定整数
DECRBY counter 5

-- 增加浮点数
SET price 9.99
INCRBYFLOAT price 0.01

-- 应用场景:计数器、限流、分布式 ID 生成

-- 示例:文章阅读计数
SET article:1001:views 0
INCR article:1001:views

-- 示例:限流(每秒最多 10 次请求)
-- 使用 INCR + EXPIRE 实现滑动窗口

-- ============================================================
--                    五、位操作(Bitmap)
-- ============================================================

-- Bitmap 使用 String 存储,每个 bit 可以是 0 或 1

-- 设置位
SETBIT user:login:20240101 1001 1    -- 用户 1001 在 20240101 登录
SETBIT user:login:20240101 1002 1    -- 用户 1002 在 20240101 登录
SETBIT user:login:20240102 1001 1    -- 用户 1001 在 20240102 登录

-- 获取位
GETBIT user:login:20240101 1001      -- 返回 1
GETBIT user:login:20240101 1003      -- 返回 0

-- 统计位为 1 的数量
BITCOUNT user:login:20240101         -- 统计 20240101 登录用户数

-- 位运算
-- AND: 两天都登录的用户
BITOP AND both_days user:login:20240101 user:login:20240102
-- OR: 任一天登录的用户
BITOP OR any_day user:login:20240101 user:login:20240102
-- XOR: 只有一天登录的用户
BITOP XOR only_one user:login:20240101 user:login:20240102
-- NOT: 取反
BITOP NOT not_login user:login:20240101

-- 查找第一个为 0 或 1 的位
BITPOS user:login:20240101 1         -- 第一个登录用户的 ID
BITPOS user:login:20240101 0         -- 第一个未登录用户的 ID

-- 应用场景:用户签到、在线状态、特征标记

-- ============================================================
--                    六、List(列表)
-- ============================================================

-- List 是双向链表,支持两端操作,适合队列、栈等场景

-- 左侧插入(头部)
LPUSH tasks "task1" "task2" "task3"

-- 右侧插入(尾部)
RPUSH tasks "task4" "task5"

-- 在指定元素前/后插入
LINSERT tasks BEFORE "task3" "task2.5"
LINSERT tasks AFTER "task3" "task3.5"

-- 获取列表长度
LLEN tasks

-- 获取指定范围的元素(0-based,-1 表示最后一个)
LRANGE tasks 0 -1       -- 获取所有
LRANGE tasks 0 2        -- 获取前 3 个

-- 获取指定位置的元素
LINDEX tasks 0          -- 第一个
LINDEX tasks -1         -- 最后一个

-- 设置指定位置的值
LSET tasks 0 "new_task1"

-- 左侧弹出
LPOP tasks

-- 右侧弹出
RPOP tasks

-- 弹出多个元素(Redis 6.2+)
LPOP tasks 2
RPOP tasks 2

-- 阻塞弹出(常用于消息队列)
BLPOP tasks 10          -- 等待 10 秒,0 表示永久等待
BRPOP tasks 10

-- 从一个列表弹出并推入另一个列表
RPOPLPUSH source dest
-- 阻塞版本
BRPOPLPUSH source dest 10

-- 移动元素(Redis 6.2+)
LMOVE source dest LEFT RIGHT

-- 删除元素
-- count > 0: 从头开始删除 count 个
-- count < 0: 从尾开始删除 |count| 个
-- count = 0: 删除所有匹配的
LREM tasks 1 "task1"

-- 保留指定范围(裁剪)
LTRIM tasks 0 99        -- 只保留前 100 个

-- 应用场景:消息队列、最近浏览、时间线

-- 示例:最近浏览的商品(保留最近 10 个)
LPUSH user:1001:recent_view "product:2001"
LTRIM user:1001:recent_view 0 9

-- ============================================================
--                    七、Set(集合)
-- ============================================================

-- Set 是无序、不重复的字符串集合

-- 添加元素
SADD tags "redis" "database" "nosql" "cache"

-- 获取所有元素
SMEMBERS tags

-- 获取元素数量
SCARD tags

-- 检查元素是否存在
SISMEMBER tags "redis"

-- 随机获取元素
SRANDMEMBER tags           -- 随机获取 1 个
SRANDMEMBER tags 3         -- 随机获取 3 个(可能重复)
SRANDMEMBER tags -3        -- 随机获取 3 个(可能重复,负数允许重复)

-- 随机弹出元素
SPOP tags                  -- 随机弹出 1 个
SPOP tags 2                -- 随机弹出 2 个

-- 移除元素
SREM tags "cache"

-- 移动元素到另一个集合
SMOVE tags new_tags "redis"

-- 集合运算
SADD set1 "a" "b" "c" "d"
SADD set2 "c" "d" "e" "f"

-- 交集
SINTER set1 set2           -- 返回 "c" "d"

-- 并集
SUNION set1 set2           -- 返回 "a" "b" "c" "d" "e" "f"

-- 差集
SDIFF set1 set2            -- 返回 "a" "b"(在 set1 但不在 set2)

-- 将结果存储到新集合
SINTERSTORE result set1 set2
SUNIONSTORE result set1 set2
SDIFFSTORE result set1 set2

-- 迭代遍历
SSCAN tags 0 MATCH r* COUNT 100

-- 应用场景:标签系统、共同好友、抽奖

-- 示例:共同关注
SADD user:1001:following "user:1002" "user:1003" "user:1004"
SADD user:1005:following "user:1002" "user:1004" "user:1006"
SINTER user:1001:following user:1005:following    -- 共同关注

-- 示例:抽奖
SADD lottery:2024 "user:1001" "user:1002" "user:1003"
SRANDMEMBER lottery:2024 3     -- 抽取 3 名幸运用户
SPOP lottery:2024              -- 抽取并移除(不能重复中奖)

-- ============================================================
--                    八、Sorted Set(有序集合)
-- ============================================================

-- Sorted Set 是有序、不重复的集合,每个元素有一个分数(score)

-- 添加元素
ZADD leaderboard 100 "player:1001"
ZADD leaderboard 95 "player:1002" 88 "player:1003" 120 "player:1004"

-- 批量添加(带选项,Redis 3.0.2+)
-- NX: 只添加新元素
-- XX: 只更新已存在的元素
-- GT: 只在新分数大于当前分数时更新
-- LT: 只在新分数小于当前分数时更新
-- CH: 返回修改的元素数量(包括新增和更新)
ZADD leaderboard NX 50 "player:1005"
ZADD leaderboard XX GT 150 "player:1001"

-- 获取元素数量
ZCARD leaderboard

-- 获取指定分数范围的元素数量
ZCOUNT leaderboard 90 100

-- 获取元素的分数
ZSCORE leaderboard "player:1001"

-- 获取元素的排名(从 0 开始)
ZRANK leaderboard "player:1001"       -- 升序排名
ZREVRANK leaderboard "player:1001"    -- 降序排名

-- 增加元素的分数
ZINCRBY leaderboard 10 "player:1002"

-- 按排名范围获取(升序)
ZRANGE leaderboard 0 -1               -- 所有元素
ZRANGE leaderboard 0 2                -- 前 3 名(分数最低的)
ZRANGE leaderboard 0 2 WITHSCORES     -- 包含分数

-- 按排名范围获取(降序)
ZREVRANGE leaderboard 0 2             -- 前 3 名(分数最高的)
ZREVRANGE leaderboard 0 2 WITHSCORES

-- 按分数范围获取
ZRANGEBYSCORE leaderboard 80 100
ZRANGEBYSCORE leaderboard 80 100 WITHSCORES
ZRANGEBYSCORE leaderboard 80 100 LIMIT 0 10    -- 分页

-- 按分数范围获取(降序)
ZREVRANGEBYSCORE leaderboard 100 80

-- 特殊语法
ZRANGEBYSCORE leaderboard -inf +inf   -- 所有
ZRANGEBYSCORE leaderboard (80 100     -- 不包含 80
ZRANGEBYSCORE leaderboard 80 (100     -- 不包含 100

-- 删除元素
ZREM leaderboard "player:1003"

-- 按排名范围删除
ZREMRANGEBYRANK leaderboard 0 1       -- 删除排名 0-1 的元素

-- 按分数范围删除
ZREMRANGEBYSCORE leaderboard 0 60     -- 删除分数 0-60 的元素

-- 集合运算
ZADD zset1 1 "a" 2 "b" 3 "c"
ZADD zset2 2 "b" 3 "c" 4 "d"

-- 并集(默认分数相加)
ZUNIONSTORE result 2 zset1 zset2
-- 指定权重
ZUNIONSTORE result 2 zset1 zset2 WEIGHTS 1 2
-- 指定聚合方式(SUM/MIN/MAX)
ZUNIONSTORE result 2 zset1 zset2 AGGREGATE MAX

-- 交集
ZINTERSTORE result 2 zset1 zset2

-- 迭代遍历
ZSCAN leaderboard 0 MATCH player:* COUNT 100

-- 应用场景:排行榜、延迟队列、时间线

-- 示例:排行榜
ZADD game:leaderboard 1000 "player:1"
ZINCRBY game:leaderboard 50 "player:1"    -- 加分
ZREVRANGE game:leaderboard 0 9 WITHSCORES -- 前 10 名

-- 示例:延迟队列(使用时间戳作为分数)
ZADD delay:queue 1704067200 "task:1001"   -- 在指定时间执行
-- 获取到期的任务
ZRANGEBYSCORE delay:queue 0 1704067200

-- ============================================================
--                    九、Hash(哈希)
-- ============================================================

-- Hash 是字段-值对的集合,适合存储对象

-- 设置字段
HSET user:1001 name "Alice" age 25 city "Beijing"

-- 获取字段
HGET user:1001 name

-- 获取多个字段
HMGET user:1001 name age city

-- 获取所有字段和值
HGETALL user:1001

-- 获取所有字段名
HKEYS user:1001

-- 获取所有值
HVALS user:1001

-- 获取字段数量
HLEN user:1001

-- 检查字段是否存在
HEXISTS user:1001 email

-- 仅当字段不存在时设置
HSETNX user:1001 email "alice@example.com"

-- 删除字段
HDEL user:1001 city

-- 字段值自增
HINCRBY user:1001 age 1
HINCRBYFLOAT user:1001 balance 10.5

-- 获取字段值的长度
HSTRLEN user:1001 name

-- 迭代遍历
HSCAN user:1001 0 MATCH * COUNT 100

-- 应用场景:存储对象、购物车、配置信息

-- 示例:购物车
HSET cart:user:1001 "product:2001" 2
HSET cart:user:1001 "product:2002" 1
HINCRBY cart:user:1001 "product:2001" 1   -- 增加数量
HDEL cart:user:1001 "product:2002"        -- 删除商品
HGETALL cart:user:1001                    -- 获取购物车

-- 示例:用户信息缓存
HSET user:1001 name "Alice" age 25 email "alice@example.com"
-- 对比 String 存储 JSON 的优势:
-- 1. 可以单独获取/修改某个字段
-- 2. 无需序列化/反序列化整个对象

-- ============================================================
--                    十、HyperLogLog
-- ============================================================

-- HyperLogLog 用于基数统计(去重计数),误差率约 0.81%
-- 优势:无论元素多少,只占用 12KB 内存

-- 添加元素
PFADD visitors:20240101 "user:1001" "user:1002" "user:1003"
PFADD visitors:20240101 "user:1001" "user:1004"    -- 重复的不会计数

-- 获取基数(去重后的数量)
PFCOUNT visitors:20240101

-- 合并多个 HyperLogLog
PFMERGE visitors:total visitors:20240101 visitors:20240102

-- 应用场景:UV 统计、独立访客数

-- 示例:网站 UV 统计
PFADD page:home:uv "192.168.1.1" "192.168.1.2"
PFCOUNT page:home:uv

-- ============================================================
--                    十一、Geo(地理位置)
-- ============================================================

-- Geo 用于存储地理位置信息,底层使用 Sorted Set

-- 添加位置(经度 纬度 名称)
GEOADD locations 116.404 39.915 "beijing"
GEOADD locations 121.473 31.230 "shanghai"
GEOADD locations 113.264 23.129 "guangzhou"
GEOADD locations 114.057 22.543 "shenzhen"

-- 获取位置坐标
GEOPOS locations "beijing" "shanghai"

-- 计算两点距离
GEODIST locations "beijing" "shanghai" km    -- 千米
GEODIST locations "beijing" "shanghai" m     -- 米

-- 获取位置的 geohash
GEOHASH locations "beijing"

-- 搜索指定范围内的位置
-- 以坐标为中心
GEORADIUS locations 116.404 39.915 500 km
GEORADIUS locations 116.404 39.915 500 km WITHCOORD WITHDIST COUNT 10 ASC

-- 以成员为中心
GEORADIUSBYMEMBER locations "beijing" 1500 km WITHDIST

-- Redis 6.2+ 新语法
GEOSEARCH locations FROMMEMBER "beijing" BYRADIUS 1500 km WITHDIST
GEOSEARCH locations FROMLONLAT 116.404 39.915 BYBOX 1000 1000 km WITHDIST

-- 应用场景:附近的人、附近的商家、配送范围

-- 示例:查找附近的商家
GEOADD shops 116.410 39.920 "shop:1001"
GEOADD shops 116.405 39.918 "shop:1002"
GEORADIUSBYMEMBER shops "shop:1001" 1 km WITHDIST

-- ============================================================
--                    十二、Stream(消息流)
-- ============================================================

-- Stream 是 Redis 5.0 引入的消息队列数据结构

-- 添加消息
XADD mystream * field1 value1 field2 value2
-- * 表示自动生成 ID,格式为 时间戳-序号

-- 指定 ID 添加
XADD mystream 1704067200000-0 field1 value1

-- 限制 Stream 长度
XADD mystream MAXLEN 1000 * field1 value1
XADD mystream MAXLEN ~ 1000 * field1 value1    -- 近似限制,性能更好

-- 获取消息数量
XLEN mystream

-- 读取消息(范围查询)
XRANGE mystream - +                            -- 所有消息
XRANGE mystream - + COUNT 10                   -- 最多 10 条
XRANGE mystream 1704067200000-0 +              -- 从指定 ID 开始

-- 反向读取
XREVRANGE mystream + - COUNT 10

-- 读取新消息(阻塞)
XREAD COUNT 10 BLOCK 5000 STREAMS mystream $   -- $ 表示最新消息
XREAD COUNT 10 BLOCK 5000 STREAMS mystream 0   -- 0 表示从头开始

-- 消费者组
-- 创建消费者组
XGROUP CREATE mystream mygroup $ MKSTREAM      -- $ 从最新开始
XGROUP CREATE mystream mygroup 0               -- 0 从头开始

-- 读取消息(消费者组)
XREADGROUP GROUP mygroup consumer1 COUNT 10 BLOCK 5000 STREAMS mystream >

-- 确认消息
XACK mystream mygroup 1704067200000-0

-- 查看待处理消息
XPENDING mystream mygroup

-- 转移待处理消息(消费者宕机时)
XCLAIM mystream mygroup consumer2 3600000 1704067200000-0

-- 删除消息
XDEL mystream 1704067200000-0

-- 裁剪 Stream
XTRIM mystream MAXLEN 1000

-- 查看 Stream 信息
XINFO STREAM mystream
XINFO GROUPS mystream
XINFO CONSUMERS mystream mygroup

-- 应用场景:消息队列、事件溯源、日志收集

💬 讨论

使用 GitHub 账号登录后即可参与讨论

基于 MIT 许可发布