页的概念
操作系统也存在页这一逻辑单位,磁盘取数据最小的基本单位。
一页 = 16Kb
show GLOBAL STATUS like 'INNODB_page_size';
select 16384/1024;
局部性原理:
- 指令1 从0x01取1kb数据到内存 磁盘io 直接取1页
- 指令2 从0x02取1kb数据到内存
磁盘io(直接读内存)
索引
INnodb在插入的时候会按照主键进行排序。
create table t1(
a int PRIMARY key,
b int,
c int,
d int,
e VARCHAR(20)
)ENGINE = INNODB;
show index from t1;
insert into t1 values(4,3,1,1,'d');
insert into t1 values(1,1,1,1,'a');
insert into t1 values(8,8,8,8,'h');
insert into t1 values(2,2,2,2,'b');
insert into t1 values(5,2,3,5,'e');
insert into t1 values(3,3,2,2,'c');
insert into t1 values(7,4,5,5,'g');
insert into t1 values(6,6,4,4,'f');
create index index_t1_bcd on t1(b,c,d); -- 重新建立一颗B+树
INnodb存储引擎辅助索引存储的是主键,MyIsam存储引擎辅助索引存储的是地址
如果INnodb存储引擎对应的表没有主键,INnodb会自动创建不可见的主键
具体Sql分析
select * from t1 where a = 7; -- a 排序
select * from t1 where b = 1 and c = 1 and d = 1; -- 走索引
explain select * from t1 where c = 1 and d = 1; -- 不能 最左前缀原则
select * from t1 where b = 1; -- 能
select * from t1 where a > 1; -- 先找a == 1,然后往后找
EXPLAIN select b,c,d,a from t1; -- 走bcd索引,bcda索引所存储的数据更少,一页可以存储更多数据,这意味着少做几次磁盘io
explain select * from t1 where b = 1 and d = 1;
-- 5.7 之前 索引,回表,过滤
-- 5.7 之后 索引,过滤,回表,索引条件下推,效率高
-- 类型不匹配的时候 字符转化为数字 0-9 转化为对应的 0-9;其他的都是0
select 1='1'; -- 1
select 0='a'; -- 1
select 1='a'; -- 0
create index idx_t1_e on t1(e); -- B+树
explain select * from t1 where a = 1; -- 1
explain select * from t1 where a = '1'; -- 1 字符转化为数字
explain select * from t1 where e = 1; -- 0
explain select * from t1 where e = '1'; -- 1
explain select * from t1 where a + 1 = 1; -- 0 虽然说理论上 这条sql等价于 explain select * from t1 where a = 1 - 1 但是mysql优化没有做到这一步
select * from t1 where a = 'a'; -- 字符‘a’会自动转换为0