mysql查询以及日志总结

1、mysql基本架构以及查询流程

  • MySQL拿到一个查询请求后,会先到查询缓存看看,之前是不是执行过这条语句。
  • 只要是你之前执行过的语句,都会在内存里面用key-value形式存储着。查询的时候就会拿着语句先去缓存中查询,如果能够命中就返回缓存的value,如果不命中就执行后面的阶段。

  • 只要对表有任何的更新,这个表的所有查询缓存就会全部被清空

  • 缓存在MySQL8.0之后就取消了。

  • 在缓存没有命中的情况下,就开始执行语句了,你写的语句有没有语法错误,这是接下来MySQL比较关心的点。

  • 会先做词法分析,你的语句有这么多单词、空格,MySQL就需要识别每个字符串所代表的是什么,是关键字,还是表名,还是列名等等。然后就开始语法分析,根据词法分析的结果,语法分析会判断你sql的对错,错了会提醒你的,并且会提示你哪里错了。

  • 之后就是优化器,因为我们建立表可能会建立很多索引,优化有一步就是要确认使用哪个索引,比如使用你的主键索引,联合索引还是什么索引更好。还有就是对执行顺序进行优化,条件那么多,先查哪个表,还是先关联,会出现很多方案,最后由优化器决定选用哪种方案。

  • 最后就是执行了,执行就交给执行器去做。

  • 参考文章

2、Mysql数据库都有哪些日志呢?分别什么作用?

  • 一般常见的有下面几种
  • binlog日志:主要是恢复数据,主从复制
  • redo log日志:保证事物中的持久化操作
  • undo log日志:回滚和多版本控制(MVCC)

3、binlog 介绍:

  • binlog记录了数据库表结构和表数据变更,比如update/delete/insert/truncate/create。它不会记录select
  • 主要有两个作用:复制和恢复数据
  • MySQL在公司使用的时候往往都是一主多从结构的,从服务器需要与主服务器的数据保持一致,这就是通过binlog来实现的

  • 数据库的数据被干掉了,我们可以通过binlog来对数据进行恢复。

  • 主从复制原理在这里插入图片描述

4、redo log 介绍:

  • 假设我们有一条sql语句:update user_table set name='java3y' where id = '3'
  • MySQL执行这条SQL语句,肯定是先把id=3的这条记录查出来,然后将name字段给改掉。
  • 实际上Mysql的基本存储结构是(记录都存在页里边),所以MySQL是先把这条记录所在的找到,然后把该页加载到内存中,将对应记录进行修改。

  • 现在就可能存在一个问题:如果在内存中把数据改了,还没来得及落磁盘,而此时的数据库挂了怎么办?显然这次更改就丢了。

  • 如果每个请求都需要将数据立马落磁盘之后,那速度会很慢,MySQL可能也顶不住。所以MySQL是怎么做的呢?

  • MySQL引入了redo log,内存写完了,会先写到buffer中,再真正落到磁盘中的redo log,这份redo log记载着这次在某个页上做了什么修改

                    

  • redo log也是需要写磁盘的,但它的好处就是顺序IO(我们都知道顺序IO比随机IO快非常多)。
  • 所以,redo log的存在为了:当我们修改的时候,写完内存了,但数据还没真正写到磁盘的时候。此时我们的数据库挂了,我们可以根据redo log来对数据进行恢复。因为redo log是顺序IO,所以写入的速度很快,并且redo log记载的是物理变化(xxxx页做了xxx修改),文件的体积很小,恢复速度很快

5、binlog和redo log区别

  • 看到这里,你可能会想:binlogredo log 这俩也太像了吧,都是用作”恢复“的。其实他俩除了"恢复"这块是相似的,很多都不一样

  • binlog记载的是update/delete/insert这样的SQL语句,而redo log记载的是物理修改的内容(xxxx页修改了xxx)。

  • 所以在搜索资料的时候会有这样的说法:redo log 记录的是数据的物理变化binlog 记录的是数据的逻辑变化

  • redo log的作用是为持久化而生的。写完内存,如果数据库挂了,那我们可以通过redo log来恢复内存还没来得及刷到磁盘的数据,将redo log加载到内存里边,那内存就能恢复到挂掉之前的数据了。

  • binlog的作用是复制和恢复而生的。

    • 主从服务器需要保持数据的一致性,通过binlog来同步数据

    • 如果整个数据库的数据都被删除了,binlog存储着所有的数据变更情况,那么可以通过binlog来对数据进行恢复。

  • 又看到这里,你会想:”如果整个数据库的数据都被删除了,那我可以用redo log的记录来恢复吗?“不能

  • 因为功能的不同,redo log 存储的是物理数据的变更,如果我们内存的数据已经刷到了磁盘了,那redo log的数据就无效了。所以redo log不会存储着历史所有数据的变更,文件的内容会被覆盖的

  • redo log是MySQL的InnoDB引擎所产生的,binlog无论MySQL用什么引擎,都会有的。

  • redo log事务开始的时候,就开始记录每次的变更信息,而binlog是在事务提交的时候才记录。

    • 如果写redo log失败了,那我们就认为这次事务有问题,回滚,不再写binlog

    • 如果写redo log成功了,写binlog,写binlog写一半了,但失败了怎么办?我们还是会对这次的事务回滚,将无效的binlog给删除(因为binlog会影响从库的数据,所以需要做删除操作)

    • 如果写redo logbinlog都成功了,那这次算是事务才会真正成功。

    • 简单来说:MySQL需要保证redo logbinlog数据是一致的,如果不一致,那就乱套了。

    • MySQL通过两阶段提交来保证redo logbinlog的数据是一致的。

6、undo log 介绍:

  • undo log主要有两个作用:回滚和多版本控制(MVCC)
  • 在数据修改的时候,不仅记录了redo log,还记录undo log,如果因为某些原因导致事务失败或回滚了,可以用undo log进行回滚
  • undo log主要存储的也是逻辑日志,比如我们要insert一条数据了,那undo log会记录的一条对应的delete日志。我们要update一条记录时,它会记录一条对应相反的update记录。
  • 这也应该容易理解,毕竟回滚嘛,跟需要修改的操作相反就好,这样就能达到回滚的目的。因为支持回滚操作,所以我们就能保证:“一个事务包含多个操作,这些操作要么全部执行,要么全都不执行
  • 因为undo log存储着修改之前的数据,相当于一个前版本,MVCC实现的是读写不阻塞,读的时候只要返回前一个版本的数据就行了。
  • 参考文章

 

 

 

 

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章