什么是乐观锁和悲观锁

乐观锁和悲观锁是数据库中常用的并发控制方式,用于处理多个用户同时访问数据库时的数据一致性问题。下面分别介绍乐观锁和悲观锁的概念和使用场景。

乐观锁

乐观锁是一种基于冲突检测的并发控制机制,它假设数据在大多数情况下不会发生冲突,因此允许多个事务并发地读取或修改数据库的同一份数据。在乐观锁机制下,每个事务在更新数据时都会先读取数据并标记版本号,然后在提交事务时检查数据的版本号是否发生过改变,若未发生改变则提交成功,否则需要根据具体的处理策略选择回滚事务或重新尝试操作。

  1. 乐观锁的实现方式主要有:
    • 版本号(Version):给每条记录增加一个版本号字段,每次更新添加 1,读取数据时先读取版本号,然后提交时根据版本号判断是否更新。
    • 时间戳(Timestamp):给每条记录增加一个时间戳字段,每次更新时记录当前时间,读取数据时先读取时间戳,然后提交时根据时间戳判断是否更新。
    • 多版本并发控制(MVCC):根据数据快照实现并发控制,不同事务之间的读写操作不会相互影响。
  2. 乐观锁的优点:
    • 适用于读取操作频繁的场景,不会对数据的读取造成阻塞。
    • 减少数据库的锁冲突和等待时间,提高了数据库的并发性能。
  3. 乐观锁的缺点:
    • 无法解决写冲突问题,需要通过回滚或者重试机制来解决并发更新的冲突。
    • 需要额外的字段来保存版本号或时间戳,增加了存储的空间。

悲观锁

悲观锁是一种基于加锁机制的并发控制方式,它假设在执行任何操作之前,其他事务可能会对数据进行修改,因此每个事务在读取或修改数据时会先加锁,确保其他事务无法访问数据,直到当前事务完成操作并释放锁。

  1. 悲观锁的实现方式主要有:
    • 行锁(Row Lock):锁定特定行的数据,保证每个事务在处理该行数据时是互斥的。
    • 表锁(Table Lock):锁定整个表的数据,保证每个事务在处理该表数据时是互斥的。
    • 意向锁(Intention Lock):在行锁和表锁之间增加了一个层级,用于协调和管理行锁和表锁之间的关系。
  2. 悲观锁的优点:
    • 保证了数据的一致性,避免了并发操作引起的冲突问题。
    • 适用于写入操作频繁的场景,可以有效地避免数据的不一致。
  3. 悲观锁的缺点:
    • 对数据库性能有一定的影响,因为需要加锁和释放锁的过程。
    • 容易产生死锁问题,需要 careful 地设计加锁的顺序。