解释一下两阶段锁定 (2PL) 协议 (DBMS)
dbmsdatabasebig data analytics更新于 2026/1/13 1:07:17
数据库的锁定和解锁应以不一致性、死锁和资源匮乏的方式进行。
2PL 锁定协议
每个事务都会在两个不同的阶段锁定和解锁数据项。
增长阶段 − 所有锁都在此阶段发出。所有数据项更改提交后,不会释放任何锁,然后开始第二阶段(收缩阶段)。
收缩阶段 −此阶段不发出任何锁,所有对数据项的更改都将被记录(存储),然后释放锁。
2PL 锁定协议的示意图如下 −

在增长阶段,事务达到一个点,即它可能需要的所有锁都已获得。这个点被称为锁点 (LOCK POINT)。
达到锁点后,事务进入收缩阶段。
类型
两阶段锁定有两种类型 −
严格两阶段锁定协议
事务可以在锁点之后释放共享锁,但在事务提交之前不能释放任何独占锁。此协议创建了一个无级联的调度方案。
级联调度:在这种调度方案中,一个事务依赖于另一个事务。因此,如果其中一个必须回滚,则另一个也必须回滚。
严格的两阶段锁定协议
事务在提交之前不能释放任何共享锁或独占锁。
2PL 协议保证可串行化,但不能保证不会发生死锁。
示例
设 T1 和 T2 是两个事务。
T1=A+B 且 T2=B+A
| T1 | T2 |
|---|---|
| Lock-X(A) | Lock-X(B) |
| 读取 A; | 读取B; |
| Lock-X(B) | Lock-X(A) |
此处:
Lock-X(B):由于 B 已被 T2 锁定,因此无法执行 Lock-X(B)。
Lock-X(A):由于 A 已被 T1 锁定,因此无法执行 Lock-X(A)。
在上述情况下,T1 等待 B,T2 等待 A。等待时间永无止境。两个事务都无法继续进行,至少任何一方主动释放锁。这种情况称为死锁。
等待图如下 −

等待图:用于死锁检测方法,为每个事务创建一个节点,如果 Ti 正在等待锁定 Tj 锁定的某个项,则创建一条指向 Tj 的边 Ti。等待图 (WFG) 中的循环表示发生了死锁。等待图会定期创建。

