一条更新语句的执行过程

上一篇,已经写了查询语句的执行过程,那么更新语句难道还不一样?

答案是肯定的。

一、更新准备

update语句其实都会有一个隐藏的查询更能,将需要修改的数据找到,然后才能更新。

其实这一阶段跟查询是一样的。

二、更新

既然获取到了数据,那么要更新,这接下来的事都是与查询sql多操作的了。

先知识扩展一下:

1.mysql中的日志

这里只介绍三种日志:

1)binlog日志

二进制日志,也叫归档日志。它是mysql中server层的日志。

2)redo log

重做日志,是innodb层面的日志。它保证了事物的持久性。这里涉及到了WAL技术,先写日志,在写磁盘。

3)undo log

回滚日志,用于事物回滚的。它保证了事物的原子性。

注:

一、undo log不是redo log的逆向日志。

1)redo log是物理日志,记录的是一个页的修改,它与更新数据无关。即redo log没有能力去更新数据库的一条数据。它的作用是如果意外重启,将数据库与其不一样的数据页加载到内存,根据redo log更新页,这时候的页与数据库中的页不一致,称为脏页。最终数据落盘,称刷脏页。这个刷脏页的过程与redo log一点关系也没有。

2)undo log 是记录的某个版本,是逻辑日志,根据某行进行恢复。

二、redo log的写入

redo log日志是先写入一个redo log buffer缓存中,然后间隔1s或者达到其内存一半时,write到怕page cache中,然后持久化到磁盘。这个过程中,也会存在未提交的事物被持久化到磁盘的情况。

2.mysql中的锁

事物的四个特性:

原子性、一致性、隔离性、持久性。

上面我们已经知道了原理性、持久性是由日志来实现的。那么一致性和隔离性呢?

为了保证原子性,引入了隔离性,那么隔离性又怎么处理呢?

答案是使用锁。

mysql的默认隔离级别是可重复读,那我们更新一条数据,如何使用锁来实现隔离性呢?

讨论是在有更新where条件有索引的基础上进行:

1)更新条件是非唯一索引

这里涉及到了回表,假如如下sql:

update user set age='30' where name='b'

其中name是非唯一索引。

2)当name是唯一索引

3)主键索引

知识点储备到这里,那么update更新怎么操作的,

1)获取锁,获取不到就没有修改的权限,就直接等待就行了。

2)写日志,将undo log、redo log、binlog写入。

3)刷脏页到磁盘,这个时间不定。

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值