导读:本期聚焦于小伙伴创作的《什么是悲观锁和乐观锁?两者的定义和适用场景分别是什么》,敬请观看详情,探索知识的价值。以下视频、文章将为您系统阐述其核心内容与价值。如果您觉得《什么是悲观锁和乐观锁?两者的定义和适用场景分别是什么》有用,将其分享出去将是对创作者最好的鼓励。

在并发编程和数据库操作场景中,当多个线程或事务同时操作同一份共享数据时,很容易出现数据不一致的问题,悲观锁和乐观锁就是用来解决这类并发冲突的两种核心思路,两者的定义和实现逻辑存在明显差异。

什么是悲观锁和乐观锁?两者的定义和适用场景分别是什么

悲观锁的定义

悲观锁的核心思想是假设并发冲突一定会发生,因此在操作数据之前就会先对数据进行加锁,整个操作过程中其他线程或事务无法对该数据进行修改,直到当前操作完成释放锁之后,其他线程才能获取锁进行操作。

悲观锁的典型实现包括数据库的行锁、表锁,以及Java中的synchronized关键字、ReentrantLock等。以数据库为例,使用SELECT ... FOR UPDATE语句就可以对查询到的行加悲观锁:

-- 开启事务
START TRANSACTION;
-- 对id为1的用户行加悲观锁,其他事务无法修改该行直到当前事务提交
SELECT balance FROM user WHERE id = 1 FOR UPDATE;
-- 执行余额修改操作
UPDATE user SET balance = balance - 100 WHERE id = 1;
-- 提交事务,释放锁
COMMIT;

悲观锁的优势是能完全避免并发冲突导致的数据不一致问题,但是因为加锁会阻塞其他操作,所以并发性能相对较低,适合写操作频繁、冲突概率高的场景。

乐观锁的定义

乐观锁的核心思想是假设并发冲突不会发生,因此操作数据时不会直接加锁,而是在更新数据的时候判断数据是否被其他线程或事务修改过,如果没有被修改则更新成功,否则更新失败,需要重试或者提示用户。

乐观锁通常通过在数据表中增加版本号字段或者时间戳字段来实现,更新时携带版本号进行比对。以下是基于版本号的乐观锁实现示例:

-- 查询数据时获取当前版本号
SELECT id, balance, version FROM user WHERE id = 1;
-- 假设查询到的version是5,更新时判断版本号是否匹配
UPDATE user SET balance = balance - 100, version = version + 1 WHERE id = 1 AND version = 5;

如果更新语句返回的影响行数为0,说明版本号不匹配,数据已经被其他事务修改过,当前更新失败。在Java代码中也可以结合版本号实现乐观锁逻辑:

public boolean updateBalanceWithOptimisticLock(int userId, int amount, int oldVersion) {
    // 执行更新操作,比对版本号
    String sql = "UPDATE user SET balance = balance - ?, version = version + 1 WHERE id = ? AND version = ?";
    int affectedRows = jdbcTemplate.update(sql, amount, userId, oldVersion);
    // 影响行数大于0说明更新成功,否则失败
    return affectedRows > 0;
}

乐观锁不需要加锁阻塞其他操作,并发性能更高,但是如果冲突概率高,会导致大量更新失败重试,反而降低效率,适合读操作频繁、冲突概率低的场景。

两者的核心区别对比

为了更清晰地理解两种锁的差异,我们可以从以下几个维度进行对比:

对比维度悲观锁乐观锁
加锁时机操作数据前加锁更新数据时判断冲突
实现方式数据库锁、显式锁机制版本号、时间戳比对
并发性能较低,会阻塞其他操作较高,无阻塞
适用场景写多读少、冲突概率高读多写少、冲突概率低

使用注意事项

在实际开发中选择锁机制时,需要结合业务场景判断:如果业务中对数据一致性要求极高,且写操作占比大,优先选择悲观锁;如果读操作远多于写操作,且冲突发生概率低,优先选择乐观锁。另外使用乐观锁时需要注意重试机制的设计,避免无限重试导致系统资源耗尽。

悲观锁乐观锁并发控制数据库锁修改时间:2026-07-23 11:51:33

免责声明:​ 已尽一切努力确保本网站所含信息的准确性。网站内容多为原创整理与精心编撰,观点力求客观中立。本站旨在免费分享,内容仅供个人学习、研究或参考使用。若引用了第三方作品,版权归原作者所有。如内容涉及您的权益,请联系我们处理。
内容垂直聚焦
专注技术核心技术栏目,确保每篇文章深度聚焦于实用技能。从代码技巧到架构设计,为用户提供无干扰的纯技术知识沉淀,精准满足专业提升需求。
知识结构清晰
覆盖从开发到部署的全链路。AI、前端、编程、数据库、服务器、建站、系统层层递进,构建清晰学习路径,帮助用户系统化掌握开发与运维所需的核心技术。
深度技术解析
拒绝泛泛而谈,深入技术细节与实践难点。无论是数据库优化还是服务器配置,均结合真实场景与代码示例进行剖析,致力于提供可直接应用于工作的解决方案。
专业领域覆盖
精准对应开发生命周期。从前端界面到后端编程,从数据库操作到服务器运维,形成完整闭环,一站式满足全栈工程师和运维人员的技术需求。
即学即用高效
内容强调实操性,步骤清晰、代码完整。用户可根据教程直接复现和应用于自身项目,显著缩短从学习到实践的距离,快速解决开发中的具体问题。
持续更新保障
专注既定技术方向进行长期、稳定的内容输出。确保各栏目技术文章持续更新迭代,紧跟主流技术发展趋势,为用户提供经久不衰的学习价值。