在表 13.2 中。冲突的锁定模式在这里我们看到ROW EXCLUSIVE与SHARE、SHARE ROW EXCLUSIVE、EXCLUSIVE和ACCESS EXCLUSIVE锁定模式冲突,但它不与自身冲突。 考虑以下示例。 我同时启动 2 个事务 T1 和 T2。
然后在T1我执行以下命令:
my_db=# begin;
BEGIN
my_db=*# update t set color = 'green' where id = 2;
UPDATE 1
然后在T2我执行以下命令:
my_db=# begin;
BEGIN
my_db=*# update t set color = 'blue' where id = 2;
之后T2 被锁定。
然后我选择关系的所有锁t:
my_db=# select lock.locktype,lock.mode,lock.transactionid,lock.relation::regclass as relation,lock.virtualxid from pg_locks as lock where locktype = 'relation';
locktype | mode | transactionid | relation | virtualxid
----------+------------------+---------------+-------------+------------
relation | RowExclusiveLock | | t_color_idx |
relation | RowExclusiveLock | | t |
relation | RowExclusiveLock | | t_color_idx |
relation | RowExclusiveLock | | t |
relation | AccessShareLock | | pg_locks |
(5 rows)
my_db=#
我看到只有RowExclusiveLock和AccessShareLock模式的锁。 但T2已被锁定。 但根据表13.2。冲突的锁定模式 RowExclusiveLock 与自身不冲突。
好吧,RowExclusiveLock与ACCESS EXCLUSIVE冲突。 考虑新的示例:我同时启动 2 个new 事务 T1 和 T2。 在T1:
my_db=# begin;
BEGIN
my_db=*#
my_db=*# alter table t alter column color TYPE varchar(400);
ALTER TABLE
my_db=*#
在T2:
my_db=# begin;
BEGIN
my_db=*# update t set color = 'black' where id = 2;
T2 在之后变得锁定,就像第一个示例一样。
然后我选择关系的所有锁t:
my_db=# select lock.locktype,lock.mode,lock.transactionid,lock.relation::regclass as relation,lock.virtualxid from pg_locks as lock where locktype = 'relation';
locktype | mode | transactionid | relation | virtualxid
----------+---------------------+---------------+-------------+------------
relation | AccessShareLock | | pg_locks |
relation | RowExclusiveLock | | t |
relation | AccessShareLock | | t_color_idx |
relation | AccessExclusiveLock | | t_color_idx |
relation | AccessExclusiveLock | | 3028689 |
relation | ShareLock | | t |
relation | AccessExclusiveLock | | t |
(7 rows)
my_db=#
我看到还有AccessExclusiveLock。 根据表13.2。冲突的锁定模式 RowExclusiveLock 与 AccessExclusiveLock 冲突。 但是第二个示例中的行为与第一个示例中的行为相同:T2 被锁定。
那么,
我预计冲突意味着锁定。
如果两种锁定模式发生冲突,则两个不同的事务不能在同一个对象上同时获取它们。第一个到来的获取锁,第二个被阻塞,直到第一个释放锁(提交)。
SHARE
锁是防止表上所有并发数据修改的锁,由CREATE INDEX
获取。 ROW EXCLUSIVE
是想要在表上执行 INSERT
、UPDATE
或 DELETE
的事务所采用的锁。出于明显的原因,它与 SHARE
锁冲突,并且它与自身不冲突,因为允许两个并发事务同时修改同一个表中的数据(只要它们不尝试修改相同的行,这由行锁处理)。