MYSQL索引
2021-12-09 17:53:32 2 举报
MySQL索引
作者其他创作
大纲/内容
600
普通索引
2
查询下一条k是否等于5
返回存储
500
开始
否
字符串和数字做比较的话,是将字符串转换成数字。
索引 k
后台操作
(\"王五\",10)
主键索引(ID)
回表
100
下条数据姓名是否为张开头
page1
唯一索引
page2
在联合索引树上查找姓名取的ID
会先根据varchar的长度截取数据,然后查询
联合索引(姓名,年龄)
在ID索引树上查找ID取得R
存储
R2
在k索引树上查找3取的ID300
结束
redo log (ib-log-fileX)
redo log 主要节省的 是随机写磁盘的 IO 消耗(转成顺序写)change buffer 主要节省的则是随机读磁盘 的 IO 消耗。
写入change buffer
主键 ID
是
有
\
隐式类型转换
200
查找 * where 姓名 = 张%
1
change buffer
数据截断
select * from tradelog where tradeid=110717; 等价于 select * from tradelog where CAST(tradid AS signed int) = 110717
二级索引(k)
带 change buffer 的更新过程
将数据从磁盘读入内存
判断年龄是否=10
(非聚簇索引)
插入或者更新
(索引下推) v5.6
select * from trade_detail where tradeid=$L2.tradeid.value; 等价于 select * from trade_detail where CONVERT(traideid USING utf8mb4)=$L2.tradeid.value;
4
system table space(ibdata1)
6
数据页是否在内存中
(聚簇索引)
(\"张六\",30)
(\"李四\",20)
300
关于 change buffer
(\"张三\",10)
read page1
索引失效
条件字段函数操作
(覆盖索引)
隐式字符编码转换
直接更新内存
400
(建议尽量选择普通索引)
(\"张三\",20)
7
在k索引树上查找k取的ID
read page2
5
1.新增主键时,新的值向后追加。2.插入主键时,其他主键数据向后移动,为该主键空出位置。 如果当前数据页满了,需要申请新的数据页,会打破数据磁盘存储的连贯性,称为页分裂,查询性能降低。 删除主键时也会有页合并。 3.主键长度越小,普通索引的叶子节点就越小,普通索引占用的空间也就越小。
判断有无冲突
插入或更新值
查找 * where 姓名 = 张三
在联合索引树上查找姓名开头为张,取得ID
联合索引
1.change buffer 在下一次数据页读入到内存(查询)的时候,会进行merge。除此之外,系统后台会有线程定期merge。shutdown时也会merge。2.change buffer 也会持久化到磁盘上。当服务器宕机重启时,会重新读取到内存中。3.对于写多读少的场景适用,如果更新后马上读取,这种场景应该关闭change buffer,其他情况都能提升性能。
3
R5
查询 select id from T where k=5
结果回表2次如果只查询 ID 和 k 则不需要回表
在联合索引树上查找姓名开头为张,取的ID
B+ tree
查找k between 3 and 5
R1
...
R4
InnoDB buffer pool (内存)
R3
new change buffer item\
在k=5,取得记录
select * from table_a where b='1234567890abcd';
查找 k=3 的数据
表结构
无
MySQL Innodb 引擎的数据存储结构是B+树,B+树是一种N叉树,一般N≈1200 。每一个索引都是一个B+树。
性能较高
对索引字段做函数操作,可能会破坏索引值的有序性,因此优化器就决定放弃走树搜索功能。去进行全索引检索,甚至全表扫描。
在ID索引树上查找ID=300取得R3
带 change buffer 的读过程
是回表
性能差不多
数据
change buffer 和 redo log
下条数据姓名是否为张三
k是否大于5
700
0 条评论
回复 删除
下一页