红魔咖啡馆

头发越掉越多,头发越掉越少

0%

【MySQL】锁

锁是计算机协调多进程或线程并发访问某一资源的机制,数据库中的数据也是一种供多用户共享的资源,需要保证数据并发访问的一致性、有效性。锁冲突也是影响数据库并发访问性能的一个重要因素。

全局锁

全局锁是对整个数据库实例加锁,加锁后整个实例就处于只读状态,后续的DML写、DDL和已经更新操作的事务提交语句都会阻塞

应用场景是做全库的逻辑备份,对所有的表进行锁定,从而获取一致性视图,保证数据的完整性

典型应用是做全库的逻辑备份,保证获取一致性视图

添加全局锁:flush tables with read lock;

特点:

  • 主库上备份,备份期间不能更新,业务停摆
  • 从库上备份,备份期间不能执行主库同步过来的二进制日志,导致主从延迟

表级锁

每次操作锁住整张表,锁定力度大,发生冲突概率最高,并发度最低

表锁

分为两类:

  • 表共享读锁:不会阻塞其他客户端的读,但会阻塞其他客户端的写
  • 表独占写锁:阻塞其他客户端的读和写

语法:

加锁:lock tables 表名... read/write;

释放锁:unlock tables

元数据锁

简称MDL,加锁过程是系统自动控制,无需显式调用,在访问一张表的时候会自动加上

主要作用是为了维护数据一致性,避免DML和DDL的冲突

当对一张表进行增删改查时,加MDL读锁(共享),当对表结构进行变更时,加MDL写锁(排他)

意向锁

为了避免DML时行锁与表锁的冲突,意向锁可以减少表锁对行锁的检查

当加行锁时,会给表添加意向锁,接下来加表锁时先判断该表锁是否能与意向锁兼容,若不能则阻塞

分类:

  • 意向共享锁(IS):由SELECT... LOCK I N SHARE MODE添加
  • 意向排他锁(IX):由INSERT、UPDATE、DELETE、SELECT FOR UPDATE等添加

行级锁

每次操作锁住对应行数据,发生锁冲突的概率最低,并发度最高,应用于InnoDB引擎中,它是通过对于索引上的索引项加锁实现的

行锁

类型:

  • 共享锁(S):允许一个事务去读一行,阻止其他事务获得相同数据集的排他锁
  • 排他锁(X):允许获取排他锁的事务更新数据,阻止其他事务获得相同数据集的共享锁和排他锁

SQL对应加锁的类型:

默认情况下,InnoDB在RR事务隔离下运行,使用next-key锁进行搜索和索引扫描发,防止幻读

  • 针对唯一索引检索时,对已存在的记录进行等值匹配时,会自动优化为行锁
  • 不通过索引条件检索数据,InnoDB会对表中所有记录加锁,升级为表锁

间隙锁/临键锁

  • 索引上的等值查询(唯一索引),给不存在的记录加锁时,优化为间隙锁
  • 索引上的等值查询(普通索引),向右遍历时最后一个值不满足查询需求时,next-key退化为间隙锁
  • 索引上的范围查询(唯一索引)会访问到不满足条件的第一个值为止

间隙锁唯一目的是防止其他事务插入间隙,可以共存

间隙锁锁的是间隙,不包括范围两端

临键锁会锁定当前数据与当前数据前的数据