MySQL 行级锁

MySQL Row level locks

我不确定行级锁是如何工作的,但这是我的问题 我有一个 table T (id int, balance int) (engine = InnoDB),我想锁定 ID = 1 的行,所以我开始这样的事务:

start transaction ; 
select * from T where ID = 1 FOR UPDATE ; 

在发送提交之前,我想尝试一下这些行是否真的被锁定了。所以我开始了另一个会话并输入:

UPDATE T set balance = balance  + 100 where ID = 1 ;

在这里我清楚地看到我在等待锁(30 秒后超时)。

但是当我输入时:

UPDATE T set balance = balance  + 8500 where ID = 2 ;

我也在等待锁定,那么我怎样才能只锁定 ID = 1 行而不是完全锁定 table?

您需要在id 列上添加索引以确保您获得行级锁。 SELECT ... FOR UPDATE 锁定执行查询时读取的所有行,而不仅仅是实际选择的行。没有索引,它必须执行完整的 table 扫描,因此每一行都会被锁定。

有了索引,它只是在该索引条目中加锁,它不必读取任何其他行,因此不会锁定其他行。