索引数据结构:
目前大部分数据库系统及文件系统都采用B Tree或者B+Tree作为索引结构
B树:每个节点存储m/2到M个关键字,非叶子节点储存指向关键字范围的子节点的指针或者某节点详细数据;所有关键字在整棵树中出现,且只出现一次,非叶子节点可以命中。
B+树:在B+树的基础上,为叶子节点增加链表指针,所有关键字都在叶子节点中出现,非叶子节点作为叶子节点的索引;B+树总是到叶子节点才能命中。
B*树:在B+树的基础上,为非叶子节点也增加链表指针,将节点的最低利用率从1/2提高到2/3
MySql(默认使用InnoDB引擎),将记录按照页的方式进行管理,每页大小默认为16k(这个值可以修改),Linux默认页大小为4k
3阶的B+树,包含2层索引,每个索引节点4bytes,最后一层要存数据,假设数据大小也是4bytes,最后一层一个叶子节点是4+4 = 8
(4*1024/4) * (4*1024/4) * (4*1024/8) = 500 000 000 约为5亿个key/value数据
为什么使用 B tree或者B+Tree
红黑树也可用来实现索引,但是文件系统及数据库系统普遍采用B Tree或者B+ Tree,为什么?
一般来说,索引本身也很大,不可能全存内存,往往以索引文件的行驶存在磁盘
1.单节点能储存更多数据,使得磁盘IO次数更少
2.叶子节点形成有序链表,便于执行范围操作
3.聚集索引中,叶子节点的data直接包含数据;非聚集索引中,叶子节点储存数据地址的指针
索引分类:
1.普通索引index:加速查找
2.唯一索引:
主键索引:primary key : 加速查找 + 约束 (不为空且唯一)
唯一索引:unique:加速查找 + 约束(唯一)
3.联合索引:
联合主键索引:primary key(id,name)
联合唯一索引:unique(id,name)
联合普通索引:index(id,name)
聚簇索引和非聚簇索引:
聚簇索引和非聚簇索引使用的都是B+树结构
1.非聚簇索引
非聚簇索引的叶子节点为索引节点,但是有一个指针指向数据节点
MyISAM是非聚簇索引
2.聚簇索引
聚簇索引的叶子节点就是数据节点
关于聚簇索引,InnoDB会按照如下规则进行处理;
1.如果一个主键被定义了,那么这个主键就是作为聚簇索引
2.如果没有主键被定义,那么该表的第一个唯一非空索引会被作为聚簇索引
3.如果没有主键也诶有合适的唯一索引,那么InnoDB内部会生成一个隐藏的主键作为聚簇索引,这个隐藏的主键是一个6个字节的列,该列的值会随着数据的插入而自增。
InnoDB的普通索引,唯一索引,联合索引都是辅助索引,采用非聚簇索引,采用非聚簇索引结构。InnoDB的所有辅助索引都引用主键作为data域。
聚集索引这种实现方式使得按主键的搜索十分高效,但是辅助索引搜索需要检索两遍索引:首先检索索引获取主键,然后用主键到主索引中检索获得记录,这个过程叫做回表