键空间
在 Redis 中管理键:键过期、扫描、修改和查询键空间
Redis 键是二进制安全的;这意味着你可以使用任何二进制序列作为键,从 "foo" 这样的字符串到 JPEG 文件的内容。空字符串也是一个有效的键。
关于键的其他一些规则
- 非常长的键不是一个好主意。例如,1024 字节的键不仅在内存方面是一个坏主意,而且在数据集中查找键可能需要进行多次昂贵的键比较。即使手头任务是匹配大值的存在,对其进行哈希处理(例如使用 SHA1)也是一个更好的主意,尤其是在内存和带宽方面。
- 非常短的键通常不是一个好主意。如果你可以写 "user:1000:followers",那么写 "u1000flw" 作为键就没有什么意义。后者更具可读性,并且与键对象本身和值对象所使用的空间相比,增加的空间很小。虽然短键显然会消耗更少的内存,但你的工作是找到合适的平衡点。
- 尝试坚持使用一个模式。例如,“object-type:id”是一个好主意,如“user:1000”。点或破折号通常用于多字字段,如“comment:4321:reply.to”或“comment:4321:reply-to”。
- 允许的最大键大小为 512 MB。
更改和查询键空间
有一些命令未在特定类型上定义,但在与键空间交互时很有用,因此可用于任何类型的键。
例如,EXISTS
命令返回 1 或 0 以表示给定键在数据库中是否存在,而 DEL
命令删除键和关联值,无论该值是什么。
> set mykey hello
OK
> exists mykey
(integer) 1
> del mykey
(integer) 1
> exists mykey
(integer) 0
从这些示例中,您还可以看到 DEL
本身如何根据键是被移除(存在)还是不存在(没有该名称的键)返回 1 或 0。
有很多与键空间相关的命令,但上述两个命令与 TYPE
命令一起是必不可少的,后者返回存储在指定键中的值的类型
> set mykey x
OK
> type mykey
string
> del mykey
(integer) 1
> type mykey
none
键过期
在继续之前,我们应该了解一个重要的 Redis 特性,它适用于您存储的任何类型的值:键过期。键过期允许您为键设置超时,也称为“生存时间”或“TTL”。当生存时间过去时,键将自动销毁。
有关键过期的几个重要说明
- 它们可以使用秒或毫秒精度设置。
- 但是,过期时间分辨率始终为 1 毫秒。
- 有关过期的信息会在磁盘上复制和持久化,当您的 Redis 服务器停止时,时间实际上会过去(这意味着 Redis 会保存键过期的时间)。
使用 EXPIRE
命令设置键的过期时间
> set key some-value
OK
> expire key 5
(integer) 1
> get key (immediately)
"some-value"
> get key (after some time)
(nil)
由于第二个调用延迟了 5 秒以上,因此键在两次 GET
调用之间消失了。在上面的示例中,我们使用了 EXPIRE
来设置过期时间(它还可以用于为已经具有过期的键设置不同的过期时间,例如 PERSIST
可用于删除过期时间并使键永久持久化)。但是,我们还可以使用其他 Redis 命令创建带有过期时间的键。例如,使用 SET
选项
> set key 100 ex 10
OK
> ttl key
(integer) 9
上面的示例设置了一个键,其字符串值为 100
,过期时间为十秒。稍后,调用 TTL
命令以检查键的剩余生存时间。
要以毫秒为单位设置和检查过期时间,请查看 PEXPIRE
和 PTTL
命令,以及 SET
选项的完整列表。
导航键空间
扫描
要以高效的方式对 Redis 数据库中的键进行增量迭代,可以使用 SCAN
命令。
由于 SCAN
允许进行增量迭代,每次调用仅返回少量元素,因此可以在生产中使用它,而不会像 KEYS
或 SMEMBERS
等命令那样存在缺点,这些命令在针对大量键或元素集合调用时可能会长时间(甚至几秒钟)阻塞服务器。
然而,虽然像 SMEMBERS
这样的阻塞命令能够提供集合中某个时刻的所有元素。SCAN
命令系列仅对返回的元素提供有限的保证,因为我们在迭代过程中增量迭代的集合可能会发生变化。
键
迭代键空间的另一种方法是使用 KEYS
命令,但应谨慎使用此方法,因为 KEYS
会阻塞 Redis 服务器,直到返回所有键。
警告:将 KEYS
视为仅应在生产环境中极其谨慎地使用的命令。
KEYS
在针对大型数据库执行时可能会破坏性能。此命令旨在用于调试和特殊操作,例如更改键空间布局。请勿在常规应用程序代码中使用 KEYS
。如果你正在寻找一种在键空间子集中查找键的方法,请考虑使用 SCAN
或 集合。
支持的 glob 风格模式
h?llo
匹配hello
、hallo
和hxllo
h*llo
匹配hllo
和heeeello
h[ae]llo
匹配hello
和hallo,
但不匹配hillo
h[^e]llo
匹配hallo
、hbllo
,... 但不匹配hello
h[a-b]llo
匹配hallo
和hbllo
如果你想逐字匹配特殊字符,请使用 \
转义它们。