浅谈Mysql原理与优化(五)——并发与锁

事务

数据库一个很重要的功能就是事务。

所谓事务一个很简单的例子就是:现在我要交易给你一百块钱,这个交易,对于数据库意味着我的余额减100,你的余额加100两个操作。事务需要保证不管出现任何意外的情况,在其他人看来,这个两个操作要么都成功,要么都失败。
浅谈Mysql原理与优化(五)——并发与锁

“在其他人看来"这点很重要,因为我们当前会话的数据库的操作总是有先有后,但是我们要保证对于其同时进行的其他查询会话的数据一致性。

那么如何实现事务呢,一般是通过锁机制或者并发机制来实现的。

比较简单的方式是通过锁来实现的。这个方式就好比告诉其他人“我们两个在交易过程中,谁也不许看” 只有等我们交易完了,其他人才能查询我们的余额。

浅谈Mysql原理与优化(五)——并发与锁

简单的概括来说有以下几个特点

  1. 读操作和写操作冲突,不能同时操作,不同会话的读操作之间不冲突。
  2. 冲突时后面的操作会等待,影响并发性能
  3. update等写操作会自动加锁,但是读操作如果需要限制并发,则需要手动加锁,有下面两种。

select… lock in share mode 表锁

select … for update 行锁,如果存储引擎支持的话

这种方式比较简单粗暴,由于锁冲突的时候会产生等待,并发性能能会明显下降。

多版本并发

这是一种更加复杂,但是性能更好的方案。简单的来说就是“交易过程中其他人可以看,但是看到的是我们交易完成前的录像”,在数据库中,其他人查询并不需要等待,但是查询到的是事务开始前的快照,

浅谈Mysql原理与优化(五)——并发与锁

这是InnoDB默认使用的方案。写会产生锁,但是读不需要持有锁,读写不冲突,所以并发性能高。

锁加在哪里

我们前边讲过,Innodb中,主键和数据共同构成表的数据结构,Innodb的锁是行锁,主要是加在主键记录上(还有一种间隙锁会锁住主键的间隙),类似于下图所示

浅谈Mysql原理与优化(五)——并发与锁

值得注意的是,如果你通过了索引过滤了数据,是会锁住索引过滤后的主键记录,这并不会锁住很多数据而影响并发性。

浅谈Mysql原理与优化(五)——并发与锁

但是如果你的语句没有用到索引,而是使用了一个全表扫描,那很不幸,你所有扫描到的数据都会加锁,即使你最后只获得一条数据。这时候就会很大的影响你系统的并发能力了。

以上就是MySQL的并发与锁的机制,希望能对大家高并发系统的设计有所帮助。

上一篇:UVA 586 Instant Complexity


下一篇:探索Oracle数据库升级6 11.2.0.4.3 Upgrade12c(12.1.0.1)