mysql 几个常用锁机制

锁分两种:乐观锁,悲观锁
之前一直以为乐观锁的性能比悲观锁好是因为不用加for update锁,后来发现其实不然,查阅了资料后发现乐观锁和悲观锁的区别是:

观锁:在取数据时锁住那几行,其他对这几行的更新需要等到悲观锁结才能继续 
乐观所:取数据,更新时检查是否数据已被更新,如果是取消当前更新 
一般在悲
观锁的等待时间过长而不能接受才会选择乐观锁

从数据库sql语句角度看,悲观锁一般使用select * from table where condition for update,这个是进行一个强制锁记录的操作。而乐观锁一般是使用update table set xxx=xxx where condition and version=${version},一般通过版本号来限制需要更新的记录版本。
之前一直以为select ... for update的效率不高,其实这个和update是一样的,都会对符合where条件的记录加锁。mysql的锁分为三种,行级锁、区间锁、next-key锁,具体可以参考:http://dev.mysql.com/doc/refman/5.7/en/innodb-locking.html

所以可以知道,乐观锁的性能之所以比悲观锁好,原因不是因为sql语句的不同,而是因为加锁时间的不同。悲观锁认为记录被修改的冲突概率较大,所以在对记录操作前就将记录锁定,然后更新记录,最后提交,所以提交的成功率很高,但是造成的并发能力较低。而乐观锁认为修改记录的冲突概率很小,所以在更新记录之前不会锁记录,而是在最后提交的时候提交锁,这样锁定记录的时间较短,并发能力较高,但是冲突概率就提高了。乐观锁一般会使用一个版本号概念,目的是记录当前记录的版本,如果当前记录没有被修改,那么相应的版本就不会改变。在更新记录的时候通过版本号来限定更新记录的版本,起到防止并发更新的问题。

数据库中有记录,可以通过乐观锁或者悲观锁进行锁定记录。
乐观锁:update tablename set version=version+1 where key=${key} and version=${version},判断update结果影响的行数。将乐观锁放在一个事务中,通过行级锁进行控制。一个事务占用了行级锁,另一个事务无法获得锁,会产生两种情况,一种是等待锁超时,一种是版本变更,update失败。

如果没有记录,可以通过insert + 唯一索引的机制进行锁定,比较暴力,通过锁表


事务隔离级别对于读取是有影响的,对于数据可见性效果不同。默认级别repeatable read可以支持mvcc,做到事务隔离。但是read commited是无法做到mvcc的。使用时候需要注意。事务隔离只是对于读取有影响。
  • 0
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值