MySQL(单表访问)

今天是新年,祝大家新年快乐,但是生活还是得继续。
请添加图片描述

后面也会持续更新,学到新东西会在其中补充。
建议按顺序食用,欢迎批评或者交流!
缺什么东西欢迎评论!我都会及时修改的!
大部分截图和文章采用该书,谢谢这位大佬的文章,在这里真的很感谢让迷茫的我找到了很好的学习文章。我只是加上了自己的拙见我只是记录学习没有任何抄袭意思
MySQL 是怎样运行的:从根儿上理解 MySQL - 小孩子4919 - 掘金小册

MySQL Server有一个称为查询优化器的模块,一条查询语句进行语法解析之后就会被交给查询优化器来进行优化,优化的结果就是生成一个所谓的执行计划,这个执行计划表明了应该使用哪些索引进行查询,表之间的连接顺序是啥样的,最后会按照执行计划中的步骤调用存储引擎提供的方法来真正的执行查询,并将查询结果返回给用户

CREATE TABLE single_table (
    id INT NOT NULL AUTO_INCREMENT,
    key1 VARCHAR(100),
    key2 INT,
    key3 VARCHAR(100),
    key_part1 VARCHAR(100),
    key_part2 VARCHAR(100),
    key_part3 VARCHAR(100),
    common_field VARCHAR(100),
    PRIMARY KEY (id),
    KEY idx_key1 (key1),
    UNIQUE KEY idx_key2 (key2),
    KEY idx_key3 (key3),
    KEY idx_key_part(key_part1, key_part2, key_part3)
) Engine=InnoDB CHARSET=utf8;

为这个single_table表建立了1聚簇索引4二级索引,分别是:

  • id列建立的聚簇索引。

  • key1列建立的idx_key1二级索引。

  • key2列建立的idx_key2二级索引,而且该索引是唯一二级索引。

  • key3列建立的idx_key3二级索引。

  • key_part1、key_part2、key_part3列建立的idx_key_part二级索引,这也是一个联合索引。

#借用评论区一位大佬写的存储过程
DELIMITER //
CREATE PROCEDURE InsertRecords()
BEGIN
DECLARE i INT DEFAULT 1;

WHILE i <= 10000 DO
INSERT INTO single_table (key1, key2, key3, key_part1, key_part2, key_part3, common_field) VALUES
(CONCAT('Key1_', i), i, CONCAT('Key3_', i), CONCAT('Part1_', i), CONCAT('Part2_', i), CONCAT('Part3_', i), 'CommonField');
SET i = i + 1;
END WHILE;
END //

DELIMITER ;

CALL InsertRecords();

访问方法(access method)的概念

查询的执行方式大致分为下边两种:

  • 使用全表扫描进行查询
    每一行记录都扫一遍,把符合搜索条件的记录加入到结果集就完了。
  • 使用索引进行查询
    因为直接使用全表扫描的方式执行查询要遍历好多记录,所以代价可能太大了
    如果查询语句中的搜索条件可以使用到某个索引,那直接使用索引来执行查询可能会加快查询执行的时间
    • 针对主键或唯一二级索引的等值查询
    • 针对普通二级索引的等值查询
    • 针对索引列的范围查询
    • 直接扫描整个索引
      MySQL执行查询语句的方式称之为访问方法或者访问类型

const

SELECT * FROM single_table WHERE id = 1438;

在这里插入图片描述
MySQL会直接利用主键值聚簇索引中定位对应的用户记录
在这里插入图片描述
对于single_table表的聚簇索引就是id列
B+树叶子节点中的记录是按照索引列排序的,对于聚簇索引来说,它对应的B+树叶子节点中的记录就是按照id列排序的。

唯一二级索引列来定位一条记录的速度也是很快的。注意这里是唯一

SELECT * FROM single_table WHERE key2 = 3841;

在这里插入图片描述
在这里插入图片描述
第一步:先从idx_key2对应的B+树索引中根据key2列与常数的等值比较条件定位到一条二级索引记录
第二步:再根据该记录的id值聚簇索引中获取到完整的用户记录

通过主键或者唯一二级索引列常数的等值比较来定位一条记录是像坐火箭一样快的,所以把这种通过主键或者唯一二级索引列来定位一条记录的访问方法定义为:const,意思是常数级别的,代价是可以忽略不计的。
不过这种const访问方法只能在主键列或者唯一二级索引列一个常数进行等值比较时才有效,如果主键或者唯一二级索引是由多个列构成的话,索引中的每一个列都需要与常数进行等值比较,这个const访问方法才有效(这是因为只有该索引中全部列都采用等值比较才可以定位唯一的一条记录)。
对于唯一二级索引来说,查询该列为NULL值的情况比较特殊,比如这样:

SELECT * FROM single_table WHERE key2 IS NULL;

在这里插入图片描述

唯一二级索引列并不限制 NULL 值的数量,所以上述语句可能访问到多条记录,也就是说 上边这个语句不可以使用const访问方法来执行。

ref

对某个普通的二级索引列常数进行等值比较

SELECT * FROM single_table WHERE key1 = 'abc';

在这里插入图片描述
对于这个查询,我们当然可以选择全表扫描

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值