数据库常用的锁

MySQL三种锁机制

MySQL各存储引擎使用了三种类型(级别)的锁定机制:表级锁定,行级锁定和页级锁定。

注:锁有多粒度的概念,也就是指可以锁定的资源的层次。SQL Server中能够锁定的资源粒度包括:数据库、表、区域、页面、键值(指带有索引的行数据)、行标识符(RID,即表中的单行数据)。

表级锁

1.表级锁:是MySQL中锁定粒度最大的一种锁,表示对当前操作的整张表加锁,它实现简单,资源消耗较少,获取锁和释放锁的速度快且不会出现死锁,但是锁冲突概率高、并发度低,主要被一些非事务性存储引擎使用,适用于以查询为主,少量更新的应用。表级锁分为表共享读锁(共享锁)与表独占写锁(排他锁)。

行级锁

2.行级锁:是MySQL中锁定粒度最小的一种锁,表示只针对当前操作的行进行加锁。行级锁发生锁冲突的概率最低,并发度也高,但加锁的开销大,加锁慢,容易出现死锁。适用于对事务完整性要求较高的系统,行级锁分为共享锁和排他锁。

页级锁

3.页级锁:是MySQL中锁定粒度介于行级锁和表级锁之间的一种锁。会出现死锁,并发度一般。

MySQL常用存储引擎的锁机制:

MyISAM和MEMORY采用表级锁;
BDB采用页级锁或表级锁,默认为页面锁;
InnoDB支持行级锁和表级锁,默认为行级锁。

InnoDB行级锁类型:

1.共享锁:又称读锁,就是多个事务对同一个数据共享一把锁,都能访问到数据,但是只能读,不能修改。用来确认某行记录是否存在,并确保没有人对这个记录进行UPDATE或者DELETE操作,如果当前事务也需要对该记录进行更新操作,则很有可能造成死锁。

2.排他锁:又称写锁,就是不能与其他锁并存,如一个事务获取了一个数据行的排他锁,其他事务就不能再获取该行的其他锁,只有获取排他锁的事务可以对数据进行读取和修改。适用于锁定行记录后需要进行更新操作的应用。

3.意向锁:是InnoDB自动加的,不需要用户干预。可以提高效率,意向锁之间是互相兼容的,意向共享锁与普通共享锁之间是兼容的,即:
在这里插入图片描述

避免死锁的方法:

(死锁:两个或两个以上的进程在执行过程中因争夺资源造成的相互等待的现象)
1.如果不同程序会并发存取多个表,尽量约定以相同的顺序访问表,可以大大降低死锁机会;
2.在同一个事务中,尽可能做到一次锁定所需要的所有资源,减少死锁产生概率;
3.对于非常容易产生死锁的业务部分,可以尝试使用升级锁定颗粒度,通过表级锁定来减少死锁产生的概率。

乐观锁和悲观锁:

乐观锁:在操作数据时非常乐观,认为别人不会同时修改数据,因此乐观锁不会上锁,只是在执行更新的时候判断一下在此期间别人是否修改了数据:如果别人修改了数据则放弃操作,否则执行操作。适用于写比较少的情况(多读场景),即冲突真的很少发生的时候,这样可以省去了锁的开销,加大了系统的整个吞吐量。

悲观锁:在操作数据时比较悲观,认为别人会同时修改数据。因此操作数据时直接把数据锁住,直到操作完成后才会释放锁,上锁期间其他人不能修改数据。适用于多写的场景。

乐观锁的实现方式

悲观锁的实现方式是加锁,乐观锁的实现方式主要有两种:CAS机制和版本号机制。
CAS(Compare And Swap)操作包括了3个操作数:需要读写的内存位置(V);进行比较的预期值(A);拟写入的新值(B)。如果内存位置V的值等于预期的A值,则将该位置更新为新值B,否则不进行任何操作。许多CAS的操作是自旋的:如果操作不成功,会一直重试,直到操作成功为止。

版本号机制一般是在数据表中加上一个数据版本号version字段,表示数据被修改的次数,当数据被修改时,version值会加1.当线程A要更新数据值时,在读取数据的同时也会读取version值,在提交更新时,若刚才读取到的version值与当前数据库中的version值相等时才更新,否则重试更新操作,直到更新成功。

CAS的缺点:

1.ABA问题:如果一个变量V初次读取的时候是A值,并且准备赋值的时候检查到它仍然是A值,但是在这段时间内它的值可能被改为B值,然后又改回到A,此时CAS操作就会误认为它从来没有被修改过。对于此问题,比较有效的方案是引入版本号。

2.循环时间长开销大:自旋CAS(也就是不成功就一直循环直到成功)如果长时间不成功,会给CPU带来非常大的执行开销。针对此问题的一个思路是引入退出机制,如果重试次数超过一定阈值后就失败退出。更重要的是避免在高竞争环境下使用乐观锁。

3.功能受限:CAS只能保证一个共享变量的原子操作,即只对单个共享变量有效,当操作涉及多个共享变量时CAS无效。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值