【MySQL篇01】补充:索引体系大总结(数据库原理篇)
文章目录
- 一、 按数据结构分类 (最核心的分类维度)
- 二、 按存储组织方式分类 (与具体存储引擎强相关)
- 三、 按功能/特性分类
- 四、 不同数据库的差异 (非常重要!)
- 五、总结表格:核心索引类型概览
索引的核心目标始终是: 加速数据检索。根据不同的 数据结构、 组织方式和 适用场景,发展出了多种索引技术。以下是一个分类体系:
一、 按数据结构分类 (最核心的分类维度)
-
B 树/ B+树索引(重点):
- 思想: 多路平衡搜索树。核心是减少磁盘I/O(树的高度低,节点存储大量键值)。有序存储,支持高效的点查询、范围查询、排序和分组。
- 变体:
- B 树: 所有节点(包括非叶子节点)都可能存储数据指针。范围查询效率相对B+树低。
- B+树(主流):
- 数据只存储在叶子节点,且叶子节点通过双向链表连接。
- 非叶子节点仅存储键值和子节点指针(能容纳更多键,树更矮)。
- 优势: 范围查询效率极高(顺序扫描叶子链表)、查询路径长度稳定(所有查询到叶子)、更适合磁盘存储(节点大小匹配页大小)。
- 场景: 关系型数据库(RDBMS)的绝对主流(MySQL InnoDB/MyISAM, PostgreSQL, Oracle, SQL Server等)。适用于等值查询、范围查询(>, <, BETWEEN)、排序(ORDER BY)、分组(GROUP BY)、前缀匹配(LIKE ‘abc%’)。
- 关键概念: 聚簇索引、非聚簇索引、覆盖索引、最左前缀原则都基于此结构。
-
哈希索引 (Hash Index):
- 思想: 基于哈希表实现。对索引列计算哈希值,将哈希值映射到桶(Bucket) 中,桶内存储指向实际数据行的指针(或直接存储行数据)。
- 特点:
- 查询速度极快 (O(1) 平均复杂度): 对于精确匹配查询(=, IN)。
- 无序: 不支持范围查询、排序、前缀匹配(LIKE ‘abc%’)。仅支持等值查询。
- 冲突 (Collision): 不同键可能哈希到同一个桶,需要解决冲突(链表法、开放寻址等)。
- 内存友好: 通常在内存中效率最高。磁盘哈希索引性能受随机I/O影响大。
- 场景:
- 内存数据库(如Redis)。
- 某些数据库的特定场景(如MySQL MEMORY引擎)。
- 不适合作为通用索引(因不支持范围查询)。
-
位图索引 (Bitmap Index):
- 思想: 为索引列的每个唯一值创建一个位图 (Bitmap)。位图的长度等于表中总行数。位图中的每一位对应表中的一行:如果该行具有这个唯一值,则位为1;否则为0。
- 特点:
- 空间高效: 当列的基数 (Cardinality) 很低(唯一值很少,如性别、状态、布尔值)时,非常节省空间。
- 集合操作高效: 对多个位图进行AND, OR, NOT等位运算极其高效(CPU指令级优化),特别适合多条件的组合查询(WHERE gender=‘F’ AND status=‘ACTIVE’)。
- 更新代价高: 插入、更新、删除数据时,需要修改多个位图,锁粒度可能较大,影响并发写入性能。
- 不适合高基数列: 唯一值很多时,位图数量巨大且稀疏,空间效率低。
- 场景: 数据仓库(OLAP)、报表系统、低基数列上的复杂条件过滤。Oracle, SQL Server, PostgreSQL等支持。
-
全文索引 (Full-Text Index):
- 思想: 专门用于在文本数据中进行关键词搜索。核心是理解词语(分词)、处理同义词、词干化(stemming)等,并建立词语到文档的映射。
- 数据结构:
- 倒排索引 (Inverted Index) 是主流: 记录每个词语(Term)出现在哪些文档(或记录)中,以及在文档中的位置信息。本质上是一个“词语 -> 文档列表”的映射。
- 也可能结合B-Tree等结构来存储词汇表。
- 特点:
- 支持自然语言查询、模糊匹配、相关性排序。
- 通常忽略停用词(Stop Words, 如“的”、“and”、“the”)。
- 场景: 搜索引擎、文档管理系统、包含大量文本字段的数据库(如文章内容、产品描述)。MySQL (InnoDB/MyISAM FULLTEXT), PostgreSQL (tsvector/tsquery), Elasticsearch (核心就是分布式倒排索引) 等支持。
-
空间索引 (Spatial Index / R-树):
- 思想: 专门用于存储和查询空间数据(点、线、面、多维数据)。核心数据结构是 R-树 (Rectangle Tree) 及其变种(如R*-Tree)。
- 原理: 将空间对象用其最小边界矩形 (MBR - Minimum Bounding Rectangle) 表示。非叶子节点存储子节点MBR的并集。通过树结构快速过滤掉不相关的区域。
- 特点: 支持空间关系查询(相交、包含、邻近等)。
- 场景: 地理信息系统 (GIS)、位置服务 (LBS)。MySQL (SPATIAL index using R-Tree), PostgreSQL (PostGIS extension using GiST/SP-GiST/R-Tree), Oracle Spatial 等支持。
-
其他/特殊索引:
- Trie树/前缀树: 用于字符串前缀匹配、自动补全。Redis的有序集合底层有时用类似结构。
- LSM-Tree (Log-Structured Merge-Tree): 不是传统意义上的查询索引,而是一种写优化的存储结构(顺序写),牺牲部分读性能(可能需要合并多个SSTable)。常用于NoSQL(如LevelDB, RocksDB, Cassandra, HBase)。其上的“索引”通常也是基于布隆过滤器+文件内索引(如SSTable的块索引)。
- GiST (Generalized Search Tree), SP-GiST (Space-Partitioned GiST), GIN (Generalized Inverted Index), BRIN (Block Range INdex): PostgreSQL提供的可扩展索引框架/类型,可以基于它们实现多种索引策略(如范围、全文、空间、数组等)。
二、 按存储组织方式分类 (与具体存储引擎强相关)
补充:聚簇索引,非聚簇索引详解
-
聚簇索引 (Clustered Index):
- 索引的叶子节点直接存储整行数据。
- 表数据物理存储顺序与聚簇索引顺序一致(或高度相关)。
- 一个表只能有一个聚簇索引(因为数据只能按一种物理顺序存储)。
- 优势: 主键/范围查询极快(数据就在旁边)、减少I/O。
- 劣势: 插入速度可能受位置影响(需要保持有序)、更新主键代价高。
- 代表: InnoDB (主键即聚簇索引)。
-
非聚簇索引 (Non-Clustered Index) / 辅助索引 (Secondary Index):
- 索引的叶子节点存储的是指向数据行的指针(在InnoDB中,这个指针是主键值;在MyISAM中,是数据文件的偏移量)。
- 表数据物理存储顺序与非聚簇索引顺序无关。
- 一个表可以有多个非聚簇索引。
- 优势: 创建灵活,对写入影响相对较小(只需更新索引本身)。
- 劣势: 查询非索引列需要回表(通过指针去主存储查找数据),增加额外I/O。
- 代表: InnoDB (所有自定义索引)、MyISAM (所有索引)。
三、 按功能/特性分类
- 唯一索引 (Unique Index): 确保索引列(或列组合)的值在整个表中是唯一的。主键索引是特殊的唯一索引(且NOT NULL)。
- 主键索引 (Primary Key Index): 表的主键列自动创建的索引(通常是聚簇索引,如InnoDB;也可能是非聚簇索引,如MyISAM)。非空且唯一。
- 普通索引 (Normal Index / Non-Unique Index): 最基本的索引类型,仅加速查询,不强制唯一性。
- 联合索引 / 复合索引 (Composite Index / Compound Index): 在多个列上建立的单个索引。遵循最左前缀原则。
- 前缀索引 (Prefix Index): 只对列值的前N个字符建立索引。用于大文本字段(如VARCHAR(255)),节省索引空间。但会降低索引选择性,可能影响准确性。
- 覆盖索引 (Covering Index): 不是一种独立索引类型! 是一种查询优化现象。当查询所需的所有列都包含在一个非聚簇索引的叶子节点中时(索引本身包含的列 + 主键),数据库可以直接返回结果,避免回表。利用现有索引达到的优化效果。
四、 不同数据库的差异 (非常重要!)
- MySQL:
InnoDB
: 默认存储引擎。聚簇索引(主键)、B+Tree、支持唯一/普通/联合/全文/空间索引。非聚簇索引存主键值。- MyISAM: 非聚簇存储(数据.MYD + 索引.MYI)。所有索引(包括主键)都是非聚簇的(叶子存数据文件偏移量)。支持全文索引(早期)。B+Tree。
- PostgreSQL: 默认使用堆表(Heap Table),数据无序存储。索引独立于数据(都是非聚簇的,叶子存指向堆元组的TID)。支持B-Tree、Hash、GiST、SP-GiST、GIN、BRIN等多种强大索引。功能非常丰富。
- Oracle: 支持B-Tree、位图、函数索引、反向键索引、域索引等。有IOT(索引组织表,类似聚簇索引)。
- SQL Server: 支持聚簇索引、非聚簇索引(B-Tree)、列存储索引、空间索引、全文索引、XML索引等。
五、总结表格:核心索引类型概览
索引类型 (按数据结构) | 核心思想/结构 | 主要优势 | 主要劣势 | 典型应用场景 | 常见支持数据库 |
---|---|---|---|---|---|
B/B+ 树(重点) | 多路平衡树,有序存储 | 高效范围查询、排序、点查,稳定,磁盘友好 | 写入可能需分裂合并 | 通用RDBMS查询 (等值、范围) | MySQL, PgSQL, Oracle, SQL Srv |
Hash | 哈希表,桶映射 | 极快等值查询 (O(1)) | 不支持范围/排序,冲突处理 | 内存表、精确匹配缓存 | Mem DBs, MySQL MEMORY, PgSQL |
Bitmap | 位图,按值标记行 | 低基数组合查询极快 (位运算) | 高基数空间大,更新代价高 | 数据仓库、低基数列过滤 (状态、类型) | Oracle, PgSQL, SQL Srv |
Full-Text (倒排) | 词语->文档映射,分词 | 自然语言搜索,关键词匹配 | 索引大,查询复杂度较高 | 文本搜索、内容管理系统 | ES, MySQL FTI, PgSQL tsvector |
Spatial (R-树) | 空间对象MBR,区域划分 | 高效空间关系查询 | 结构相对复杂 | 地理信息系统 (GIS), LBS | MySQL Spatial, PgSQL PostGIS |