这张图看起来很正确.
我假设您的示例中的pk
是InnoDB表的主键,因此是聚集索引.
间隙从大于97的一个值开始锁定,并一直延伸到无穷大.
这似乎很奇怪,因为值98和99看起来应该没有锁,因为条件为WHERE pk > 99
,因此与值98或99不匹配.但是Next-key锁锁定索引记录之前的whole gap,直到但不包括前面的索引记录.
https://dev.mysql.com/doc/refman/8.0/en/innodb-locking.html#innodb-next-key-locks表示:
索引记录上的Next-key锁也会影响该索引记录之前的"间隙".也就是说,Next-key锁是索引记录锁加上索引记录前面的间隙上的间隙锁.
演示:在第一个窗口中,我启动了一个获取Next-key锁的事务:
mysql> select * from mytable;
+-----+-------+
| pk | name |
+-----+-------+
| 3 | hello |
| 97 | hi |
| 101 | hola |
| 103 | yo |
| 107 | hey |
+-----+-------+
mysql> start transaction;
mysql> select * from mytable where pk > 99 for update;
+-----+------+
| pk | name |
+-----+------+
| 101 | hola |
| 103 | yo |
| 107 | hey |
+-----+------+
现在锁定了PK 101的索引记录,以及PK 97之后的差距.
在第二个窗口中,我测试了以下内容:
mysql> insert into mytable values (99, 'test');
(hangs)
mysql> insert into mytable values (98, 'test');
(hangs)
mysql> update mytable set name='test' where pk=97;
Query OK, 1 row affected (0.00 sec)
Rows matched: 1 Changed: 1 Warnings: 0