Key
- 显而易见,key不要太长,否则浪费内存,在可读性和长度间取个平衡;
- Keys命令,返回满足条件的key,时间复杂度O(n),n为db中的key数量,生产环境慎用;
- Scan命令,通过增量迭代的方式提供类似Keys的功能,迭代过程中的信息存储到游标并返回给客户端,服务端并不记录迭代的任何信息,因此,支持多客户端并发迭代,支持客户端中途停止迭代。每次调用的时间复杂度是O(1),一次完整迭代的时间复杂度为O(n)。但Scan命令有以下限制:
- 支持指定每次返回的count,但不提供任何保证;
- 集合中的一个元素在迭代过程中可能会返回多次,客户端能处理重复的情况;
- 迭代过程中,集合中有元素新增或删除,该元素有可能返回,也有可能不返回;
- Expire/TTL相关指令,用于设置失效时间;
- Sort排序指令,时间复杂度O(N+M*log(M)),N为集合的元素个数,M为返回的集合数,耗时较高,可根据情况分到Salve节点中执行;
String
Redis服务端并不关心Value格式,所以String其实就是byte数组。该数据结构一般用于缓存,存任何你想存得东西。
- get/set系列命令,基本都是O(1)级别的时间复杂度,非常爽;
- incr/decr系列指令,Redis原生的计数器实现,非常适合实时计数的需求;
- setex指令,带过期时间的set原子操作,和缓存功能完美匹配;
- setbit/getbit/bitop,直接操作bit位,想知道怎么玩?(传送门)
Hash
相当于带field的String,比String类型更结构化。多数操作都是O(1)级别的时间复杂度,各种快,用于缓存或内存数据库。
List
由于List是一个双向的链表,可用于支持各种需要队列的业务中,操作都是O(1)复杂度(同时处理多个元素的命令除外,如LTRIM),还提供Block版本的API,好得不能再好。
Set
带去重功能的集合,匹配类似于好友列表之类的业务场景。除了smembers外,针对单个元素的操作都是O(1),同时提供sinter、sunion等取交集和并集的操作。
SortedSet
可以指定权重的去重有序集合,可用于需要支持排序的场景。zadd/zrem的复杂度是O(logn),1亿个元素也就20+。但像ZRangeByScore/ZRemRangeByScore这样的命令,时间复杂度为O(logn+M)(n为集合中元素个数,M为操作的元素个数),如果M很大的话,效率也不好。