mysql RR级别各种锁表现演示

1.表结构

CREATE TABLE `transaction_test` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`a` int(10) DEFAULT NULL,
`b` int(10) DEFAULT NULL
PRIMARY KEY (`id`),
KEY `idx_a` (`a`)
) ENGINE=InnoDB AUTO_INCREMENT=21 DEFAULT CHARSET=utf8;

陈述:范围查询加锁是加在索引上,等值查询是锁行,没有索引即锁表。

演示没有索引字段加锁,锁全表。

 

演示普通索引等值更新

1.等于存在的值,左开右闭,锁住(5,10]区间。

 

 

 

 此时,更新不存在的值不受影响:

 2.等于一个不存在的值,左开右开,锁住(5,10)区间,更新同样不存在的值不受影响。

 

演示等值唯一索引 

CREATE TABLE `transaction_test` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`a` int(10) DEFAULT NULL,
`b` int(10) DEFAULT NULL,
`c` int(10) DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `idx_c` (`c`) USING BTREE,
KEY `idx_a` (`a`)
) ENGINE=InnoDB AUTO_INCREMENT=21 DEFAULT CHARSET=utf8;

1.等于唯一索引,行锁,只锁住一行,通过其他条件(比如id)更新该行数据同样会被阻塞。

 

 通过主键id同样是锁行,根据其他条件更新该行数据会阻塞。

 

  2.加锁在唯一索引上,但是值不存在,左开右开,锁住(5,10)间隙,更新同样不存在的值不受影响。

 主键id上的加锁情况同上。

 

 3.插入数据,当前行加锁:

 

演示普通索引范围搜索

1.锁住范围最大最小值的左开右闭间隙(5,10],但是,范围查询是锁索引,根据id可以更新a=10那条记录

 

 

演示唯一索引范围搜索

1.锁住范围最大最小值的左开右闭间隙(5,10],同上,范围查询是锁索引,根据id可以更新c=10那条记录

 

 2.锁住(5,15]间隙,同上,范围查询是锁索引,根据id可以更新c=15那条记录

 

 演示唯一索引范围查询:

1.锁住范围最大最小值的左开右闭间隙(5,10],同上,范围查询是锁索引,根据id可以更新c=10那条记录

 

 2.主键id范围查询,锁住id(5,9)区间,跟别的索引不一样的是,这里不能通过其他索引条件更新id=9的记录:

 

6.select lock in share mode,锁范围同上,只能加S锁,不能加X锁(如果先加S锁的事物,在后面加X锁时未有其他事物加S锁,则当前事物允许加X锁,后面的事物只能按已有X锁处理,即不能再加S锁了),当前读操作均为X锁(select for update,update,insert,delete)

原文地址:https://www.cnblogs.com/reboot30/p/15589440.html