MySQL中redo日志和undo日志简述

redo日志

  • 磁盘的随机IO和顺序IO
    随机IO即IO操作的地址是随机的不连续的,顺序IO是操作的磁盘地址是连续的
  • Buffer Pool
    缓冲池,也就是当读取一页数据进行一波操作后并不会立马就删除或者同步更新修改到磁盘中,而是保存在所谓的Buffer Pool中,下次用到时就不用重新读取了,因为读取磁盘的速度实在太慢太慢了。Buffer Pool的空间肯定是有限的,为了保存一直用到的数据,所以会维护一个LRU链表决定谁去谁留,还按照某个比例将LRU链表分成两半的,一部分存储使用频率非常高的缓存页,一部分反之,随着程序的运行,某个节点所属的区域也可能发生变化。这样就保证当buffer Pool满时删除的页面是不怎么访问的。
  • 刷脏
    buffer pool的存在就意味着,读取一个页面后如果修改了的话就没得及时同步刷新到磁盘里面。存在buffer pool的就是脏页。会有专门负责刷脏的线程,或者内存不够需要时会进行刷脏后删除某页,或者批量刷脏。
  • redo日志
    buffer pool还带来一个问题,当数据页在buffer pool里被修改然后没有被刷脏同步到磁盘里面持久化的话,系统崩了的话会丢失修改的部分,每次事务提交都刷脏一次也会带来问题,有时候一个页面修改一个字节,就得刷脏整个页面(一条sql语气默认是一个事务,都会分配一个事务ID),或者一个事务修改多个页,带来的随机磁盘的速度慢和刷新过多无用的浪费。MySQL里面的redo日志用来保存修改的记录,然后当脏页没有同步刷新到磁盘时,redo日志先写入磁盘,这样当系统崩时可以通过redo日志恢复。redo日志就是记录修改的地方,比如第几号表空间第几页地址偏移多少修改了啥等,好处就是,因为日志文件小比那个16k一页的数据小了很多倍,而且设计的时候,日志时存放在一个固定大小连续的空间里面,输入顺序磁盘操作速度更快。buffer pool的空间满了会触发脏页刷新,redo日志空间满了也会主动去触发刷新脏页。当脏页刷新后对应的redo日志空间就可以再利用了。
  • 日志写入磁盘的时机
    redo日志也有一个缓冲区log buffer专门存放日志缓存的,当log buffer空间不足时即log buffer的redo日志量已经占满了log buffer总容量的大约一半左右,就需要把这些日志刷新到磁盘上。每次事务提交时脏页可能不会直接刷新到磁盘进行持久化,而是刷新对应的日志文件持久化redo日志。也会有一个专门的线程对redo日志文件进行定时刷新。还有正常关闭服务器时页刷新。

undo日志

  • 事务ID
    当开始一个事务时即执行一条或者多条语气时,系统会分配给一个唯一的事务ID,用于记录修改的undo日志,因为查询语气不会产生undo的日志所以也就没必要分配给事务ID了也就是默认为0,只有碰到修改语气才会分配事务ID。一条事务下来前面查询语气的事务ID是0,到了修改那里才会分配事务ID,事务ID的分配有一个全局变量控制,当分配一个事务ID时将该全局变量赋值当作ID,然后该变量+1,也就是说保证了先分配的事务ID总是会小于后分配的事务ID,这个全局变量也不是无限变大,当达到最大后会从0开始。总之,这样做的目的是可以根据事务ID知道两个事务的先后之分,这在后面的版本链时对比事务的先后控制版本是否可读。
  • 记录结构
    在一条记录里会隐藏的保存三列一列时一个自增的ID用来索引的,还有两列是用于事务的,有一列保存事务ID,有一列保存回滚指针,其中事务ID就是改动该记录的事务ID,插入就是插入该记录的那个事务ID,修改删除也是,回滚指针是保存指向undo记录的地址的指针的。
  • undo日志
    有时候一个事务修改了一般没提交就接受需要回滚,即恢复原来没修改前的模样,MySQL就是把事务修改的记录做一个undo日志,记录修改之前的信息,比如插入记录就记录一个该记录的ID就好,回滚时直接删除,更新删除记录就记录之前版本的所有信息就好,这些日志信息会像数据一样保存在一种和数据表类型不一样的表中,也和数据页一样一页一页的保存,所以在redo日志看来都一样的页,一样更新脏页到磁盘,同一个事务产生的undo日志会链接成一个undo链。插入的undo日志在事务提交后就没用了直接删除掉,其他的日志还会在MVCC中用到所以没得删除,会有专门的线程Purge进行判断是否还可用,不可用就删除。Purge操作会克隆最老旧的read_view,如果当前运行的事务没有可以访问的undo日志就会被标记为删除进行删除。
  • 版本链
    undo日志会产生一个牛逼的东西,即所谓的版本链。一个记录的隐藏列会记录修改该记录的事务ID和指向undo日志的回滚指针,然后当这条记录再次被修改时,这些信息就会被保存在undo日志里面形成一个牛逼的版本链即图
    在这里插入图片描述
    就说某个记录对应一个事务ID值,就是这个事务修改成这样的,然后还有一个指向上一个版本的undo 日志的指针,这就是一个版本链。用处就是MVCC。
    转至《MySQ事务隔离级别和MCVV
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值