mysql中InnoDB幻读解决方案与机制

 更新时间:2026年03月06日 10:21:23   作者:萧曵 丶  
本文主要介绍了mysql中InnoDB幻读解决方案与机制,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧

InnoDB 主要通过 MVCC(多版本并发控制) 和 Next-Key Lock(临键锁) 机制来解决幻读问题,具体策略取决于事务隔离级别:

1.在可重复读(REPEATABLE READ)隔离级别下

MVCC 机制

  • 通过 Read View 机制实现快照读
  • 事务开始时创建一致性视图,后续读取都基于这个视图
  • 其他事务的插入操作不会影响当前事务的查询结果

Next-Key Lock(临键锁)

  • 记录锁(Record Lock):锁住索引记录
  • 间隙锁(Gap Lock):锁住索引记录之间的间隙
  • 临键锁 = 记录锁 + 间隙锁:锁住记录和前面的间隙

示例

-- 假设表中有记录:10, 20, 30
SELECT * FROM t WHERE id > 15 FOR UPDATE;
-- Next-Key Lock 会锁住范围 (10, 20], (20, 30], (30, +∞]
-- 阻止其他事务在这个范围内插入数据

2.解决幻读的场景分析

情况1:快照读(普通 SELECT)

-- 事务A
BEGIN;
SELECT * FROM users WHERE age > 20;  -- 返回2条记录

-- 事务B
INSERT INTO users (age) VALUES (25); -- 成功,但不影响事务A

-- 事务A再次查询
SELECT * FROM users WHERE age > 20;  -- 仍然返回2条记录(无幻读)

原理:MVCC 保持一致性视图

情况2:当前读(加锁 SELECT)

-- 事务A
BEGIN;
SELECT * FROM users WHERE age > 20 FOR UPDATE;  -- 加Next-Key Lock

-- 事务B尝试插入
INSERT INTO users (age) VALUES (25);  -- 被阻塞,等待锁释放

原理:Next-Key Lock 阻止其他事务插入

3.不同隔离级别的对比

隔离级别幻读解决方案性能影响
READ COMMITTED可能发生幻读
REPEATABLE READMVCC + Next-Key Lock中等
SERIALIZABLE完全串行化

4.实际应用建议

何时能完全避免幻读?

  • 使用 REPEATABLE READ 隔离级别
  • 查询使用索引(否则会锁全表)
  • 当前读操作(FOR UPDATE、LOCK IN SHARE MODE)

注意事项

-- 以下情况可能仍有幻读风险:
-- 1. 混合使用快照读和当前读
BEGIN;
SELECT * FROM t WHERE id > 100;           -- 快照读
UPDATE t SET name = 'test' WHERE id > 100; -- 当前读,可能看到新插入数据

-- 2. 使用 READ COMMITTED 隔离级别
SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED;

5.监控和调优

-- 查看锁信息
SHOW ENGINE INNODB STATUS;

-- 监控锁等待
SELECT * FROM information_schema.INNODB_LOCKS;
SELECT * FROM information_schema.INNODB_LOCK_WAITS;

-- 优化建议
-- 1. 合理设计索引,减少锁范围
-- 2. 避免长时间事务
-- 3. 必要时使用 SERIALIZABLE 隔离级别

总结

InnoDB 在 REPEATABLE READ 隔离级别下,通过 MVCC 解决快照读的幻读问题,通过 Next-Key Lock 解决当前读的幻读问题。但需要注意事务中混合使用不同读取方式可能带来的不一致性。

到此这篇关于mysql中InnoDB幻读解决方案与机制的文章就介绍到这了,更多相关mysql InnoDB幻读内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

您可能感兴趣的文章:

相关文章

  • mysql触发器trigger实例详解

    mysql触发器trigger实例详解

    MySQL好像从5.0.2版本就开始支持触发器的功能了,本次博客就来介绍一下触发器,首先还是谈下概念性的东西吧,需要的朋友可以参考下
    2021-03-03
  • 用Eclipse连接MySQL数据库的步骤

    用Eclipse连接MySQL数据库的步骤

    这篇文章主要介绍了如何用Eclipse连接MySQL数据库,需要的朋友可以参考下
    2015-08-08
  • 详解mysql 组合查询

    详解mysql 组合查询

    这篇文章主要介绍了详解mysql 组合查询的的相关资料,帮助大家更好的理解和使用MySQL数据库,感兴趣的朋友可以了解下
    2020-12-12
  • MySQL之库和表的操作实践

    MySQL之库和表的操作实践

    本文讲解MySQL数据库和表的操作,涵盖创建、修改、删除,字符集与校验规则设置,备份恢复方法,及查看连接状态,强调注意事项如删除风险和校验规则对大小写的影响
    2025-09-09
  • linux mysql忘记密码的多种解决或Access denied for user ''root''@''localhost''

    linux mysql忘记密码的多种解决或Access denied for user ''root''@''local

    linux mysql忘记密码的多种解决方法。
    2009-07-07
  • MySQL压测工具mysqlslap的介绍与使用

    MySQL压测工具mysqlslap的介绍与使用

    mysqlslap是mysql自带的一个性能压测工具,mysqlslap用于和其它的一些性能压测工具一样可以自己造数据进行压测。mysqlslap的报告比较简单主要体现在执行的时间方面,没有sysbench那样的tps、qps等更详细的包括。下面来一起看看关于mysqlslap的介绍和简单的使用示例。
    2016-09-09
  • MySQL 创建三张关系表实操

    MySQL 创建三张关系表实操

    这篇文章主要介绍了MySQL 创建三张关系表实操,文章说先创建学生表然后科目表和分数表三张有着密切关系的表,下文实操分享需要的小伙伴可以参考一下
    2022-03-03
  • Mysql中关于on,in,as,where的区别

    Mysql中关于on,in,as,where的区别

    这篇文章主要介绍了Mysql中关于on,in,as,where的区别说明,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2023-03-03
  • mysql 8.0.19 安装配置方法图文教程

    mysql 8.0.19 安装配置方法图文教程

    这篇文章主要为大家详细介绍了mysql 8.0.19 安装配置方法图文教程,文中安装步骤介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2020-02-02
  • Mysql中Identity 详细介绍

    Mysql中Identity 详细介绍

    这篇文章主要介绍了Mysql中Identity 的相关资料,并附示例代码,需要的朋友可以参考下
    2016-09-09

最新评论