美文网首页
InnoDB是怎样支持高并发的?

InnoDB是怎样支持高并发的?

作者: packet | 来源:发表于2019-02-21 19:31 被阅读0次

世界是由矛盾组成的,并发的矛盾是什么?线程安全和线程效率,要保证线程安全,就得保证秩序(在处理临界资源的时候),所以难免有些线程需要等待,但这样会降低吞吐量。
为什么Innodb会在当今大行其道?就是因为其有优秀的并发能力。这篇文章就主要谈谈这个问题。
Innodb控制并发的手段有两个:锁 和 MVCC
一 锁
1.普通锁:读写都加锁,本质上是串行的。
2.共享锁和排他锁(Share Locks,记为S;eXclusive Locks,记为X),只有两个共享锁不互斥,也就是说多个读操作是可以并行的,而读写操作是不能并行的。

二 MVCC
MVCC的核心思想是数据的多版本。
当有写操作的是时候,data会可克隆出一个新版本V1,写操作操作的是V1,而读操作将读取老版本V0的数据。

总结:
普通锁:串行
共享锁和排他锁:读读并行
MVCC:读写并行

那老数据是存储在什么地方呢?这里先介绍两个概念。

什么是redo日志?
数据库事务提交以后,不会马上刷新到磁盘上,因为磁盘随机IO性能太低,这样会影响数据库的吞吐量。
优化方案是将写操作先写到redo日志里,这样就变成了顺序IO,再定期刷新到磁盘上,这样就能提高效率了。
假设某个时刻数据库崩溃,有些数据还没有刷新到磁盘上,那么数据库重启后,会重做redo日志里的内容。

什么是undo日志?
数据库事务未提交时,修改前的数据的旧版本会存储在undo日志里,当数据库崩溃或者事务回滚时,会回恢复undo日志里的内容。

总结:
redo日志:保障已提交事务的acid特性
undo日志:保障未提交事务的acid特性

当数据库对数据做修改的时候,需要把数据页从磁盘读到buffer pool中,然后在buffer pool中进行修改,那么这个时候buffer pool中的数据页就与磁盘上的数据页内容不一致,称buffer pool的数据页为dirty page 脏数据,如果这个时候发生非正常的DB服务重启,那么这些数据还没在内存,并没有同步到磁盘文件中(注意,同步到磁盘文件是个随机IO),也就是会发生数据丢失,如果这个时候,能够在有一个文件,当buffer pool 中的data page变更结束后,把相应修改记录记录到这个文件(注意,记录日志是顺序IO),那么当DB服务发生crash的情况,恢复DB的时候,也可以根据这个文件的记录内容,重新应用到磁盘文件,数据保持一致。

什么是回滚段?
回滚段是undo日志的一种组织形式,UNDO内部由多个回滚段组成

现在回到MVCC,旧版本数据存储在什么地方呢?
就是存储在undo日志里。回滚段里存储的就是历史数据的快照,它们不会改变,其他事务可以肆无忌惮地读取这些数据快照。
可见,innodb高并发的实现关键就是拥有多版本并发控制(Multi Version Concurrency Control, MVCC),通过读取旧版本数据(历史数据的快照)来实现并发。

那么select读取的是什么?
select * from t where id>2;
这一句是快照读,不需要加锁。
select * from t where id>2 lock in share mode;
select * from t where id>2 for update;
这两句显式加锁,是非快照读。

以下是《高性能MySQL》中的描述:

MVCC的定义:多版本控制: 指的是一种提高并发的技术。最早的数据库系统,只有读读之间可以并发,读写,写读,写写都要阻塞。引入多版本之后,只有写写之间相互阻塞,其他三种操作都可以并行,这样大幅度提高了InnoDB的并发度。
InnoDB是在undo log中实现的,通过undo log可以找回数据的历史版本。找回的数据历史版本可以提供给用户读(按照隔离级别的定义,有些读请求只能看到比较老的数据版本),也可以在回滚的时候覆盖数据页上的数据。在InnoDB内部中,会记录一个全局的活跃读写事务数组,其主要用来判断事务的可见性。
MVCC只在 READ COMMITTED 和 REPEATABLE READ 两个隔离级别下工作。其他两个隔离级别够和MVCC不兼容, 因为 READ UNCOMMITTED 总是读取最新的数据行, 而不是符合当前事务版本的数据行。而 SERIALIZABLE 则会对所有读取的行都加锁。

参考:
MySQL-InnoDB-MVCC多版本并发控制
InnoDB并发如此高,原因竟然在这?
说说MySQL中的Redo log Undo log都在干啥

相关文章

  • InnoDB是怎样支持高并发的?

    世界是由矛盾组成的,并发的矛盾是什么?线程安全和线程效率,要保证线程安全,就得保证秩序(在处理临界资源的时候),所...

  • Mysql索引优化

    存储引擎 InnoDB InnoDB是是Mysql默认的事务性存储引擎 InnoDB才有MVCC来支持高并发,并且...

  • 锁机制

    锁机制 Innodb是事务级数据库,支持事务,支持外键,rollback,mvcc(高并发:在readcommit...

  • Mysql的存储引擎

    Mysql的存储引擎 InnoDB InnoDB采用MVCC来支持高并发,并且实现了四个标准的隔离级别,其默认级别...

  • Mysql存储引擎Innodb小结

    innodb是mysql支持事务的存储引擎,也是当前mysql默认的存储引擎。innodb支持行级别锁,对并发性事...

  • 3、说说InnoDB与MyISAM的区别

    说说InnoDB与MyISAM的区别 1、InnoDB支持事务(MVCC多版本并发控制),MyISAM不支...

  • MySql 各个存储引擎介绍

    InnoDB 1.支持行锁 2.支持外键 3.支持非锁定读 4.支持事物 5.MVCC支持高并发 聚族,所有数据都...

  • mysql使用规范

    建表规约 【强制】:①存储引擎必须使用 InnoDB 解读:InnoDB 支持事物、行级锁、并发性能更好,CPU ...

  • 读已提交(RC)与可重复读(RR)不可重复读测试步骤

    InnoDB引擎的RC与RR隔离级别都支持基于MVCC的事务并发控制,MVCC是基于“数据版本”对并发事务访问,这...

  • MySQL 锁详解

    InnoDB 锁 数据库使用锁是为了支持更好的并发,提供数据的完整性和一致性。InnoDB是一个支持行锁的存储引擎...

网友评论

      本文标题:InnoDB是怎样支持高并发的?

      本文链接:https://www.haomeiwen.com/subject/eovdyqtx.html