AUTO-INC锁

悲观者从机会中看到困难。乐观者从困难中看到机会。
——温斯顿·丘吉尔

表里的主键设置成自增的,这是通过对主键字段声明 AUTO INCREMENT 属性实现的。

之后可以在插入数据时,可以不指定主键的值,数据库会自动给主键赋值递增的值,这主要是通过AUTO-INC 锁实现的。

AUTO-INC 锁是特殊的表锁机制,锁不是再一个事务提交后才释放,而是再执行完插入语句后就会立即释放

在插入数据时,会加一个表级别的 AUTO-INC 锁,然后为被 AUTO INCREMENT 修饰的字段赋值递增的值,等插入语句执行完成后,才会把 AUTO-INC 锁释放掉。

那么,一个事务在持有 AUTO-INC 锁的过程中,其他事务的如果要向该表插入语句都会被阻塞,从而保证插入数据时,被 AUTO INCREMENT 修饰的字段的值是连续递增的。

但是, AUTO-INC 锁再对大量数据进行插入的时候,会影响插入性能,因为另一个事务中的插入会被阳塞。

因此,在 MySQL 5.1.22 版本开始,InnoDB 存储引擎提供了一种轻量级的锁来实现自增。

一样也是在插入数据的时候,会为被 AUTO_INCREMENT 修饰的字段加上轻量级锁,然后给该字段赋值一个自增的值,就把这个轻量级锁释放了,而不需要等待整个插入语句执行完后才释放锁。

InnoDB 存储引擎提供了个 innodb_autoinc_lock_mode 的系统变量,是用来控制选择用 AUTO-INC 锁还是轻量级的锁。

  • 当innodb_autoinc_lock_mode=0,就采用 AUTO-INC 锁,语句执行结束后才释放锁;

  • 当innodb_autoinc lock_mode=2,就采用轻量级锁,申请自增主键后就释放锁,并不需要等语句执行后才释放。

  • 当innodb autoinc lock mode=1:

    • 普通 insert 语句,自增锁在申请之后就马上释放;

    • 类似 insert .. select 这样的批量插入数据的语句,自增锁还是要等语句结束后才被释放;

当 innodb_autoinc_lock_mode=2是性能最高的方式,但是当搭配 binlog 的日志格式是 statement 一起使用的时候,在「主从复制的场景」中会发生数据不一致的问题

posted @ 2025-04-05 22:29  Tsukinor  阅读(55)  评论(0)    收藏  举报