Mysql默认存储引擎InnoDB和底层数据结构

在黑马点评项目实战中:谈到了为什么不推荐使用mysql的字段自增作为订单id传递给客户端,让我想到了Mysql的​​存储引擎​​和​​底层数据结构​​究竟是什么?它是如何实现自增的?本文主要是深度解析 MySQL 默认存储引擎 InnoDB 与底层数据结构 B+树,可以做一个简单了解。


一、InnoDB 是什么?—— MySQL 的“事务守护者”

InnoDB 是 MySQL 数据库中最常用的​​存储引擎(Storage Engine)​​,由 InnoDB 公司(后被 Oracle 收购)开发,专为满足企业级应用的高并发、事务性需求设计。自 MySQL 5.5 版本起,它正式成为 MySQL 的默认存储引擎,逐渐取代了早期默认的 MyISAM。

InnoDB 的核心定位是:​​支持 ACID 事务的企业级存储引擎​​。它不仅解决了传统存储引擎(如 MyISAM)不支持事务的痛点,还通过行级锁、外键约束、崩溃恢复等机制,成为高并发场景下的“数据守护者”。


二、InnoDB 的核心特性:为什么它能成为企业级首选?

InnoDB 的强大之处,在于其针对企业级需求设计的五大核心特性,这些特性直接解决了互联网高并发场景中的关键问题。

1. 事务支持(ACID 特性)—— 数据一致性的基石

InnoDB 是 MySQL 中​​唯一原生支持完整事务​​的存储引擎。它通过 UNDO LOG(回滚日志)和 REDO LOG(重做日志)实现事务的原子性(Atomicity)、一致性(Consistency)、隔离性(Isolation)和持久性(Durability)。

  • ​原子性​​:若事务执行中途失败(如网络中断),UNDO LOG 可回滚所有已修改的数据,确保“要么全做,要么全不做”。例如,用户下单时扣减库存,若支付失败,UNDO LOG 会恢复库存至下单前状态。
  • ​持久性​​:REDO LOG 记录所有已提交的事务,数据库崩溃后可通过重放日志恢复数据。例如,服务器断电前未完成的订单写入,重启后 REDO LOG 会重新执行,避免数据丢失。

这一特性让 InnoDB 成为金融交易、订单系统等对数据一致性要求极高的场景的首选。

2. 行级锁(Row-Level Locking)—— 高并发的“通行证”

传统存储引擎(如 MyISAM)仅支持表级锁,即操作整张表时需加锁,高并发下易引发“锁竞争”(多个请求排队等待锁,导致性能骤降)。而 InnoDB 支持​​行级锁​​——仅锁定需要操作的行,其他行仍可正常读写。

​示例​​:当多个用户同时修改同一张表的不同订单(如用户 A 修改订单 1,用户 B 修改订单 2),行级锁允许这两个操作并行执行,无需等待,大幅提升并发性能。相比之下,表级锁会导致两个操作排队,性能下降 90% 以上。

3. 外键约束(Foreign Key)—— 数据关联的“守护者”

InnoDB 支持外键约束,可强制维护表之间的关联关系。例如,用户表(user)与订单表(order)通过用户 ID 关联,若删除用户表中的某条记录,而订单表仍有该用户的订单引用,InnoDB 会阻止删除或自动级联删除关联订单,避免“脏数据”(无用户信息的订单)。

这对需要维护数据关联关系的业务(如电商的用户-订单系统)至关重要。试想,若用户删除后仍保留订单,系统将无法关联用户信息,导致数据混乱。

4. 崩溃恢复(Crash Recovery)—— 数据安全的“保险栓”

InnoDB 通过 REDO LOGUNDO LOG 实现高效的崩溃恢复:

  • ​REDO LOG​​:记录“已提交但未写入磁盘”的事务,数据库重启后重放这些日志,确保数据持久化。例如,服务器在写入数据到磁盘前崩溃,REDO LOG 会重新执行未完成的写入操作。
  • ​UNDO LOG​​:记录“已修改但未提交”的事务,用于回滚未完成的事务,避免数据不一致。例如,用户下单时扣减库存,若支付失败,UNDO LOG 会撤销库存扣减操作。

这一机制让 InnoDB 在面对服务器断电、网络故障等异常时,仍能保证数据的完整性,避免“数据丢失”或“脏读”。

5. 聚集索引(Clustered Index)—— 数据存储的“导航图”

InnoDB 的表数据是​​按主键顺序存储​​的(称为“聚集索引”),主键的查询效率极高。若未显式定义主键,InnoDB 会自动生成一个隐藏的 ROW_ID 作为聚集索引。

聚集索引的结构决定了数据的物理存储顺序,因此主键的选择(如自增主键)会直接影响写入性能。例如,使用自增主键时,新数据会按顺序追加到 B+树叶子节点尾部,避免随机写入导致的页分裂;而使用 UUID 作为主键,数据会随机插入,频繁触发页分裂,大幅降低写入性能。


三、InnoDB 是 MySQL 的默认引擎吗?—— 从版本演进看技术选择

InnoDB 的“默认引擎”地位并非一蹴而就,而是随着 MySQL 版本的迭代逐步确立的:

  • ​MySQL 5.1 及之前​​:默认存储引擎是 MyISAM。MyISAM 不支持事务、行级锁,仅支持表级锁,适合读多写少的静态数据场景(如字典表),但无法满足互联网高并发需求。
  • ​MySQL 5.5 及之后​​:InnoDB 成为默认存储引擎(通过 default-storage-engine=InnoDB 配置)。这一转变标志着 MySQL 从“轻量级数据库”向“企业级数据库”的转型,InnoDB 凭借事务、行级锁等特性,完美匹配了互联网高并发、强一致性的需求。

四、为什么 InnoDB 成为默认引擎?—— 对比 MyISAM 的“降维打击”

InnoDB 的崛起,本质是对 MyISAM 短板的“精准补位”。通过对比两者的核心差异,我们可以更清晰地理解 InnoDB 的优势:

​特性​​InnoDB​​MyISAM​
事务支持支持(ACID)不支持
锁粒度行级锁(高并发友好)表级锁(高并发下性能差)
外键约束支持不支持
崩溃恢复支持(REDO/UNDO 日志)不支持(需手动修复)
存储结构聚集索引(数据与主键一起存储)非聚集索引(数据与索引分离存储)
统计行数需扫描全表(无全局计数器)维护全局计数器(COUNT(*) 更快)
适用场景高并发、事务性场景(如电商、金融)读多写少、静态数据(如配置表)

​总结​​:MyISAM 适合简单查询场景,但在互联网高并发、强一致性的需求下,InnoDB 的事务、行级锁等特性使其成为不可替代的选择。


五、InnoDB 的底层数据结构:B+树——磁盘存储的“最优解”

InnoDB 的高效性,很大程度上依赖于其底层的​​数据存储结构​​。与内存数据库不同,磁盘的随机读写性能远低于内存,因此 InnoDB 必须设计一种“磁盘友好”的结构来优化 IO 效率。

5.1 B+树:InnoDB 的“索引基石”

InnoDB 的数据存储结构基于 ​​B+树(B+ Tree)​​,这是一种专为磁盘存储优化的多路平衡搜索树。它的核心结构分为两类节点:

  • ​内部节点(非叶子节点)​​:仅存储索引键值和子节点指针,用于快速定位数据范围。
  • ​叶子节点​​:存储完整的索引键值 + 对应数据的指针(或数据本身,InnoDB 中叶子节点直接存储行数据)。
  • ​叶子节点通过双向链表连接​​:形成有序的“链表”,支持高效的范围查询。
B+树的典型结构示例:

假设主键为 id,叶子节点按 id 顺序存储行数据,内部节点通过 id 范围指向子节点:

内部节点1:[id=100, 指针→内部节点2;id=200, 指针→内部节点3]  
内部节点2:[id=150, 指针→叶子节点A;id=180, 指针→叶子节点B]  
叶子节点A:[id=150, 数据指针→行1] → [id=160, 数据指针→行2] → ...(链表连接)  
叶子节点B:[id=180, 数据指针→行3] → [id=190, 数据指针→行4] → ...  

5.2 B+树的核心优势:为什么适合数据库索引?

(1)磁盘 IO 友好

数据库的数据和索引通常存储在磁盘中,而磁盘的随机读写性能远低于内存。B+树通过“多路平衡”设计,将树的高度控制在极低水平(例如,10亿数据量的 B+树,树高仅需3~4层),每次查询只需几次磁盘 IO 即可定位数据。

相比之下,二叉树(如红黑树)的树高随数据量呈对数增长(10亿数据量需约30层),每次查询需30次磁盘 IO,性能差距悬殊。

(2)范围查询高效

叶子节点的双向链表结构,使得范围查询(如 SELECT * FROM table WHERE id BETWEEN 100 AND 200)可以通过遍历链表完成,无需回退到上层节点。而红黑树的范围查询需从根节点重新遍历,效率低下。

​示例​​:查询“ID 在 150~200 之间的订单”,B+树只需遍历叶子节点链表(150→160→…→200),而红黑树需从根节点递归查找,耗时增加数倍。

(3)顺序写入优化

InnoDB 的主键索引(聚簇索引)是​​顺序写入​​的(如自增主键)。B+树的叶子节点按顺序插入时,只需在链表尾部追加,无需分裂节点(或仅少量分裂),大幅提升写入性能。

若使用非递增的主键(如 UUID),会导致 B+树叶子节点随机插入,频繁触发页分裂(Page Split),大幅降低写入性能。例如,UUID 随机生成时,B+树需不断调整节点位置,写入延迟增加 50% 以上。

(4)高并发支持

B+树的结构稳定,索引维护(如插入、删除)通过节点分裂/合并完成,对查询的影响较小。配合行级锁,能高效处理高并发场景下的读写冲突。例如,电商大促时,每秒数十万次订单写入,B+树仍能保持稳定的响应时间。


六、红黑树 vs B+树:为什么 InnoDB 不选红黑树?

红黑树是一种自平衡二叉树(每个节点最多有两个子节点),通过颜色标记(红/黑)保证树的平衡。尽管它在内存存储中表现优异(插入、删除、查询时间复杂度均为 O(log n)),但作为数据库索引却存在致命缺陷:

红黑树的局限性:

  • ​树高过大,磁盘 IO 次数多​​:10亿数据量的红黑树树高约30层,每次查询需30次磁盘 IO;而 B+树仅需3~4层,性能差距悬殊。
  • ​范围查询效率低​​:红黑树的范围查询需递归遍历子树,无法利用链表顺序访问优化。例如,查询“ID 大于 1000 的数据”,红黑树需遍历所有大于1000的节点,而 B+树只需遍历链表。
  • ​写入性能不稳定​​:插入/删除时需频繁调整节点颜色和旋转,虽然保证了平衡,但频繁的树结构调整会增加写入延迟。例如,高并发写入时,红黑树的调整操作可能导致写入延迟增加 30% 以上。

因此,红黑树更适合内存存储的小数据量场景(如 Java 的 TreeMap),而 B+树凭借“多路平衡+链表连接”的设计,成为数据库索引的“最优解”。


总结:InnoDB 与 B+树的“数据哲学”

InnoDB 选择 B+树而非红黑树,本质是为了满足​​磁盘存储的高效性​​和​​事务场景的复杂性​​。B+树通过多路平衡、顺序存储、链表连接等设计,完美解决了数据库索引的核心痛点(范围查询、高并发写入、磁盘 IO 优化)。

在黑马点评项目中,我们选择 Redis INCR 作为全局唯一ID生成方案,正是基于对 InnoDB 特性的深度理解:Redis INCR 生成的严格递增 ID,与 InnoDB 聚簇索引的顺序写入特性完美匹配,大幅提升了订单表的写入性能。

​一句话总结​​:B+树是 InnoDB 的“索引心脏”,支撑着事务、高并发和高效查询;而 InnoDB 则是企业级数据库的“数据守护者”,凭借 ACID 事务、行级锁等特性,成为互联网高并发场景的首选。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/news/915111.shtml
繁体地址,请注明出处:http://hk.pswp.cn/news/915111.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

原点安全签约金网络数科,共建一体化数据安全防护体系

金网络正式携手原点安全,基于原点安全一体化数据安全平台(uDSP),启动企业数据安全平台建设项目,围绕数据资产盘点、敏感数据识别与分类分级、数据访问权限管控、数据动态脱敏、数据安全审计与风险监测等关键能力建设&a…

mix-blend-mode的了解使用

mix-blend-mode 是 CSS 的一个属性,用于控制元素的内容(如文本、图像、背景等)如何与其 父元素 或 背景 进行混合。它类似于图形设计软件(如 Photoshop)中的图层混合模式,可以实现各种视觉效果;…

vue自定义指令bug

问题描述:页面加载时,报已下错误。同时,页面数据不显示环境介绍:已经添加了vue自定义指令permission,实现如下,用以控制元素显示权限app.directive(permission, (el, binding) > {if (!store.hasPermiss…

Vue3 + WebSocket

Vue3与WebSocket结合能够很好地满足实时通讯的需求。通过合理设计和管理WebSocket连接的生命周期,以及实现必要的重连逻辑和心跳检测机制,可以构建出响应迅速且稳定的实时应用。WebSocketWebSocket允许服务端主动向客户端发送数据,无需客户端…

IPSec和HTTPS对比(一)

IPSec(Internet Protocol Security)是网络层(OSI第3层)的加密协议,其核心机制和与HTTPS的区别如下:🔒 ​一、IPSec的核心机制解析​​1. 安全封装结构​┌──────────┬───────…

关于 c、c#、c++ 三者区别

1. 起源与定位语言起源时间开发者定位/特点C1972年Dennis Ritchie面向过程的编程语言,强调底层控制与高效性能C1983年Bjarne Stroustrup在 C 的基础上加入 面向对象编程(OOP)C#2000年微软(Microsoft)类似 Java&#xf…

项目总体框架(servlet+axios+Mybatis)

项目总体框架 先暂时这样子(后续发现错误的话就改) com.hope-tieba/ ← 项目根 ├─ .idea/ ← IDEA 工程配置 ├─ src/ │ ├─ main/ │ │ ├─ java/ │ │ │ └─ com/hope/ │ │ …

RestTemplate 实现后端 HTTP 调用详解

1. 方法签名解析方法名和返回类型说明了这个方法的业务意图和数据结构。Override 表示实现接口方法&#xff0c;利于规范开发和自动检查。Override public List<RobotInfo> listRobots() {这里 RobotInfo 是假设的业务数据结构&#xff0c;实际项目中按你的类名即可。2. …

Python单例模式详解:从原理到实战的完整指南

引言 单例模式是软件设计中最常用的模式之一&#xff0c;它确保一个类只有一个实例&#xff0c;并提供全局访问点。在Python中&#xff0c;实现单例模式有多种优雅的方式&#xff0c;本文将详细讲解6种主流实现方法&#xff0c;包含完整代码示例和注释。 一、模块级单例&#x…

拼团系统中的幂等性防护 , 前置性查询,Redis 库存预判

这段内容涉及两个关键点&#xff1a;幂等性防护 和 拼团目标量判断&#xff0c;下面我将分别解释这两个问题&#xff0c;并重点说明&#xff1a; “如果没有拦截&#xff0c;最终访问数据&#xff0c;也会有数量判断拦截。” 这句话的意思。 ✅ 1. 查询外部交易 outTradeNo 是…

【Python】LEGB作用域 + re模块 + 正则表达式

文章目录一 LEGB作用域二 re&#xff08;Regular Expression&#xff09;预览1. re.match() —— 从字符串开头匹配2. re.search() —— 搜索整个字符串3. re.findall() —— 返回所有匹配的字符串列表4. re.finditer() —— 返回所有匹配的迭代器5. re.sub() —— 替换匹配的字…

JavaSE -- 数据操作流

6. 数据操作流在执行文件存储一个对象的时候&#xff0c;如果该对象只有少量属性需要存储&#xff0c;并且这些属性的类型都是基本数据类型&#xff0c;此时则不需要对象序列化技术。使用数据操作流既可以实现。 DataOutputStreamDataInputStream 注意&#xff1a; 读取数据的时…

GI6E 加密GRID電碼通信SHELLCODE載入

GI6E https://github.com/MartinxMax/gi6e 「它似乎能從特製的音訊信號中提取敏感資訊。」 HEX-GRID CODEX&#xff08;簡稱 HGC&#xff09;是一種自定義的 6 位元結構編碼系統&#xff0c;使用三位元的群組識別碼&#xff08;Group Bits&#xff09;加上三位元的索引識別碼…

实习十三——传输层协议

补充子网划分的主要目的就是为了节约IP&#xff0c;降低成本&#xff0c;但是如果划分私有IP网段&#xff0c;则完全没有意义&#xff0c;因为私有IP可重复&#xff0c;不要钱&#xff0c;所以私有IP严禁进行子网掩码划分传输层协议TCP三次握手TCP协议数据格式第一次握手&#…

RPG59.玩家拾取物品三:可拾取物品的提示UI

1。以WarriorWidgetBase作为父类&#xff0c;创建一个子类的userwidget2.布局为两个值都为1203。然后我们需要想办法&#xff0c;在合适的位置&#xff0c;用bool来控制此控件的显示与隐藏。情况为&#xff1a;当玩家触发与可拾取物体的重叠时&#xff0c;我们将广播一个bool值…

Vue.js 国际化 (i18n) 实践:让你的应用走向全球,多语言支持如此简单!

文章目录一、为何你的 Vue.js 应用需要“说多种语言”&#xff1f;国际化的重要性二、Vue I18n 基础实践&#xff1a;从零开始搭建多语言环境2.1 安装 Vue I18n2.2 配置 Vue I18n 实例2.3 在组件中使用翻译三、进阶实践&#xff1a;让国际化更强大、更灵活3.1 动态语言切换3.2 …

在CentOS7.9服务器上安装.NET 8.0 SDK

在 CentOS 7.9 系统上手动安装 .NET 8.0 SDK&#xff08;使用本地的 dotnet-sdk-8.0.101-linux-x64.tar.gz 文件&#xff09;&#xff0c;可以按照以下步骤进行操作。由于 CentOS 7.9 已不再被微软官方支持&#xff0c;可能会遇到依赖库版本问题&#xff08;如 GLIBCXX 和 GLIB…

HarmonyOS-ArkUI Web控件基础铺垫4--TCP协议- 断联-四次挥手解析

HarmonyOS-ArkUI&#xff1a; Web组件加载流程1 HarmonyOS-ArkUI Web控件基础铺垫1-HTTP协议-数据包内容 HarmonyOS-ArkUI Web控件基础铺垫2-DNS解析 HarmonyOS-ArkUI Web控件基础铺垫3--TCP协议- 从规则本质到三次握手-CSDN博客 接上文&#xff0c;上文我们讲解了: 数据在…

如何用AI 生成论文/书籍的摘要

不知道大家是否有这样的感觉&#xff0c;上网浏览信息&#xff0c;看到好的文章就兴奋地下载了下来&#xff0c;文件的名称通常是一串奇奇怪怪的字符串。过了几天就在电脑中找不着了。没有网络上搜索不到的文章&#xff0c;而是在你的电脑中却找不到它们。几年下来&#xff0c;…

ubuntu系统+N卡 | docker compose+ollama+dify(dify和ollama在同一容器)

1、安装NVIDIA驱动 2、安装docker&#xff0c;docker compose 3、安装NVIDIA Container Toolkit Installing the NVIDIA Container Toolkit — NVIDIA Container Toolkit&#xff08;仅 GPU 场景需要&#xff09; # Configure the production repository: curl -fsSL https://…