Redis与MySQL设计_Redis设计与实现(八)数据库

24章今天一定要弄到10章!

Redis服务器将所有数据库都保存在服务器状态redis.h/redisServer结构的db数组中,db数组中的每个项都是一个redis.h/redisDb结构,每个redisDb都表示着一个数据库:

在redisServer使用一个数组来保存数据库。

1abe8ae48c5e8f6e52ad7177db4225e6.png

在初始化的时候会通过redisServer中的dbnum来决定创建多少个数据库。dbnum属性的值由服务器配置的database选项决定,默认情况下创建16个数据库。如下图所示

ab18a7a10821c7d5fda09dcb6fc45272.png

客户端可以通过SELECT命令来对数据库进切换。SELECT的逻辑就是改变指针的引用

在服务器内部是通过redisClient结构的db属性记录客户端当前目标的数据库。redisClient.db指针指向redisServier.db数组中的某一个元素。

88a650e38643329e9d72803aec9a834f.png

Redis是一个键值对的数据库,思想是极致的节省内存,每个数据库都是redisDb数组中的一个,其中redisDb中的dict字典保存了数据库中的所有键值对。成为键空间。

242d89c9280ba9e19134afbbe6f45eb3.png

但其实这肯定不符合redis的设计思想嘛,我这么多KV都放着了,肯定是不现实的,键空间对于用户选择的数据库是相对应的也就是你选择的是1号数据库那是只会存储1号数据库里面的所有KV。

7b08609f8a3272e28c9ae1c828460bdb.png

当添加一个KV进入数据库的时候,Key是SDS,而Value可以是任何一个redisObject。如果是V是一个hashtable里面就还有有一个新的dict,ht[0],ht[1]什么的

删除的时候也是常规的思想,就是把这个KV从字典的引用中去除就行了。

更新的话根据不同的RedisObject会有不同的实现。

0beac96b4e1e4a2c53064357694ea102.png

取值的操作也是一样的,先从redisDb对象里面的dict找到key,然后再从redisObjetct中去获取value。如果是hashtale 的情况可以自己思考下,应该很容易就可以想明白了

在读写键空间的时候也会有很多额外的操作

1.读取键的时候,会根据这个value是否存在,然后更新键空间中的hit 或者 miss变量。

2.读取一个键的时候,会更新这个redisObject中的lru变量,从而更新时间

3.如果读取的时候发现这个键值对已经无效了,那么就会先删除这个key然后进行余下的操作

4.如果这个value被watch了,在修改的时候就会对这个键标记为脏

5.如果修改了一个键之后,会对这个键进行计数加一。方便后续的事物程序进行管理

6.如果开启了通知,那么就会发送对应的通知消息

给Key设置存活时间,这个也是在平时开发中经常使用到的东西,通过EXPIRE或者PEXPIRE命令来进行实现,SETEX和PEXPIRE的逻辑是一样的。TTL以及PTTL是返回剩余的存活时间。

在redisDb结构中还包含了一个expires字典,也就是过期字典,用来存储已经过期的Key和过期的时间

d0afb1697c4464a2075a504d59a73aeb.png

至于如何进行删除,如果从资源分配的角度上思考,惰性删除是最好的,因为不用时时刻刻拉着一个线程进行。

970adc8b0dae44a7a1c0541432cb8af5.png

a5218e7b1367c7389f8994dacb9b7209.png

可以说惰性+定时的组合是最好的,针对业务进行时间上的choose

最后就是AOF和RDB了这个也是面试中很经常问到,一定要耐心。

在执行SAVE或者BGSAVE的时候,程序会对数据库里面的键进行check,已经过期的Key不会被保存到新建的RDB文件中。

在启动Redis服务器的时候(主服务器模式),会读取RDB中的文件,这时候也会对RDB中的数据进行check如果已经过期了就不会载入到数据库中去。如果是正常的服务器模式就会都载入进去。

如果服务器是以AOF进行运行的。当Key被过期的时候,就会想AOF中追加一条DEL命令,这个也可以看出在读取AOF是根据时间的有序性进行读取的。

在主从服务器架构中,当主服务器知道了一个key过期的时候 会向从服务器也发送一个DEL消息,让从服务器也去删除Key

从服务器遇到自身带的过期key的时候也会正常执行,从服务器只会对主服务器给的DEL消息进行执行。所以如果主从情况下,主节点一定一定要对过去的key可靠保证的发送消息。

数据库通知是2.8之后的新功能 没啥意思

a4944f687ee411a6d478dfacb16927e4.png

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值