写点什么

【Redis】概览

用户头像
awen
关注
发布于: 2021 年 06 月 07 日
【Redis】概览


准备写一个关于 Redis 的系列文章,本片从全局视角概括介绍 Redis。

Redis 是一个开源(BSD 许可)的,内存中的数据结构存储系统,它可以用作数据库、缓存和消息中间件。 它支持多种类型的数据结构,如 字符串(strings), 散列(hashes), 列表(lists), 集合(sets), 有序集合(sorted sets) 与范围查询, bitmaps, hyperloglogs 和 地理空间(geospatial) 索引半径查询。 Redis 内置了 复制(replication),LUA 脚本(Lua scripting), LRU 驱动事件(LRU eviction),事务(transactions) 和不同级别的 磁盘持久化(persistence), 并通过 Redis 哨兵(Sentinel)和自动分区(Cluster)提供高可用性(high availability)。

数据类型

Redis 支持五种数据类型:string(字符串),list(列表),hash(哈希),set(集合)及 zset(sorted set:有序集合)。

https://redis.io/topics/data-types-intro

注:后续会出单独章节介绍 Redis 数据结构及其底层实现。

string

append <key> value

set/setex/psetex/setnx/mset/msetnx/get/mget/getset/getrange/strlen

incr <key>/incrby <key> incement/incrbyfloat <key> incement


附加:bit 操作

setbit <key> offset value

getbit <key> offset

bitcount <key>

list

Redis 列表是简单的字符串列表,按照插入顺序排序。你可以添加一个元素到列表的头部(左边)或者尾部(右边)

一个列表最多可以包含 2^32 - 1 个元素 (4294967295, 每个列表超过 40 亿个元素)。

set

Redis 的 Set 是 String 类型的无序集合。集合成员是唯一不可重复的。Redis 中集合是通过哈希表实现的,所以添加,删除,查找的复杂度都是 O(1)。集合中最大的成员数为 2^32 - 1 (4294967295, 每个集合可存储 40 多亿个成员)。

zset

Redis Zset 和 Set 一样也是 string 类型元素的集合,成员也是唯一不可重复的。,但分数(score)却可以重复。zset 通过分数来为集合中的成员进行从小到大的排序。

集合是通过哈希表实现的,所以添加,删除,查找的复杂度都是 O(1)。 集合中最大的成员数为 2^32 - 1 (4294967295, 每个集合可存储 40 多亿个成员)。


hash

Redis hash 是一个 string 类型的 field(字段) 和 value(值) 的映射表,适合用于存储对象。每个 hash 可以存储 232 - 1 键值对(40 多亿)。

hyperloglogs

geo

Redis geo 主要用于存储地理位置信息,并对存储的信息进行操作

streams

Redis Stream 是 Redis 5.0 版本新增加的数据结构。

Redis Stream 主要用于消息队列(MQ,Message Queue),Redis 本身是有一个 Redis 发布订阅 (pub/sub) 来实现消息队列的功能,但它有个缺点就是消息无法持久化,如果出现网络断开、Redis 宕机等,消息就会被丢弃。

简单来说发布订阅 (pub/sub) 可以分发消息,但无法记录历史消息。而 Redis Stream 提供了消息的持久化和主备复制功能,可以让任何客户端访问任何时刻的数据,并且能记住每一个客户端的访问位置,还能保证消息不丢失。

https://redis.io/topics/streams-intro

key 管理

del <key>
dump <key>
exists <key>
expire <key> <seconds>
EXPIREAT <key> <timestamp>
keys *
OBJECT REFCOUNT <key>
OBJECT ENCODING <key>
OBJECT IDLETIME <key>
persist <key>
PEXPIRE key milliseconds
PEXPIREAT key milliseconds-timestamp
ttl/pttl <key>
randomkey
rename <key> <newkey>
RENAMENX <key> <newkey>
RESTORE key ttl serialized-value
sort key [asc|desc]
sort key alpah [asc|desc]
sort key [alpha] [asc|desc} [limit start end]
type <key>
复制代码


持久化

  • RDB

RDB 就是 Snapshot 快照存储,是默认的持久化方式。

可理解为半持久化模式,即按照一定的策略周期性的将数据保存到磁盘。

对应产生的数据文件为 dump.rdb,通过配置文件中的 save 参数来定义快照的周期。

下面是默认的快照设置:

save 900 1 #当有一条 Keys 数据被改变时,900 秒刷新到 Disk 一次

save 300 10 #当有 10 条 Keys 数据被改变时,300 秒刷新到 Disk 一次

save 60 10000 #当有 10000 条 Keys 数据被改变时,60 秒刷新到 Disk 一次

  • AOF

当使用 redis 存储非临时数据时,一般需要打开 AOF 持久化来降低进程中止导致的数据丢失。AOF 可以将 redis 执行的每一条写命令追加到硬盘文件中,这一过程显然会降低 redis 的性能,但是大部分情况下这个影响是可以接受的,另外使用较快的硬盘可以提高 AOF 的性能。

  • 开启 appendonly yes

  • 重写机制

  • 随着执行的命令越来越多,AOF 文件的大小也会越来越大,冗余的命令会越来越多。redis 可以自动优化 AOF 文件,每当达到一定条件时 redis 就会自动重写 AOF 文件。这个条件可以在配置文件中配置:

    auto-aof-rewrite-percentage 100

    auto-aof-rewrite-min-size 64mb

    auto-aof-rewrite-percentage 参数的意义是当目前的 AOF 文件大小超过上一次重写时的 AOF 文件大小的百分之多少时会再次进行重写,如果之前没重写过,则以启动时的 AOF 文件大小为依据。

    auto-aof-rewrite-min-size 参数限制了允许重写的最小 AOF 文件大小,通常在 AOF 文件很小的情况下即使其中有很多冗余的命令我们也不太关心。除了让 redis 自动执行重写外,我们还可以主动使用 BGREWRITEAOF 命令手动执行 AOF 重写。

  • 同步机制 appendfsync

  • always

  • everyseconds

  • no

进阶

缓存过期

过期策略

  • 定时过期

为每一个设置了过期时间的 key 设置一个定时器,对 cpu 不友好

  • 惰性过期

使用 key 才检查是否过期,对内存不友好,如果 key 长时间不访问容易导致内存不足

  • 定期过期

这种方案,每隔一定时间,会扫描一定数量的数据库的 expires 字典一定数量的 key,并清除其中已经过期的 key

Redis 使用惰性过期与定期过期相结合的方式,过期策略对 rdb 及 aof 模式均没有影响

命令

expire <key> time

ttl <key>

persist <key>

淘汰键策略

  • volatile-lru 使用 LRU 算法删除一个键(只对设置了过期时间的键)

  • allkeys-lru 使用 LRU 算法删除一个键

  • volatile-random 随机删除一个键(只对设置了过期时间的键)

  • allkeys-random 随机删除一个键

  • volatile-ttl 删除过期时间最近的一个键

  • noeviction

    volatile-lfu 使用 LFU 算法删除一个键(只对设置了过期时间的键)

  • allkeys-lfu 使用 LFU 算法删除一个键

事务

https://redis.io/topics/transactions

  • DISCARD

  • EXEC

  • MULTI

  • UNWATCH

  • WATCH

注:后续会出单独章节介绍 Redis 事务。

数据迁移工具

  • 阿里巴巴:https://github.com/alibaba/RedisShake

    唯品会:redis-migrate-tool

pipline

https://redis.io/topics/pipelining

注:后续会出单独章节介绍 Redis pipline。

高可用

  • 主从复制

  • 哨兵模式

  • Cluster

客户端

  • jredis

  • lettuce

  • redisson

业务应用场景

缓存

排行榜

基于 zset,将分数作为 score,然后做排序查询

分布式锁

基于 setnx

基于 redlock

在线用户数

SETBIT "online_users" <user_id> 1

GETBIT "online_users" <user_id>

BITCOUNT "online_users"

注意:仅统计在线用户数不关心具体在线用户的话,可以使用基数统计替代

最新列表

基于 zset,将更新时间设置为 score,然后做排序查询

队列

基于 list 的普通队列

基于 zset 的优先级队列

基数统计

基于 hyperloglogs

用户头像

awen

关注

Things happen for a reason. 2019.11.15 加入

还未添加个人简介

评论

发布
暂无评论
【Redis】概览