Mysql索引的使用

8.索引相关
    
    8.0 联合索引和最左匹配原则
    
        最左匹配原则:以最左边的起点任何连续的索引都能匹配上。同时遇到范围查询(>、<、between、like、in)就会停止匹配。
        
        联合索引:combine_index(a, b, c); 根据最左匹配规则,用到索引的子集为以下两种情况:
        情况一:第一列匹配,后面可以缺失n列
            a
            a, b
            a, c(只用到了索引a,效果等同于a)
        情况二:完全匹配所有列
            a, b, c
        以上的匹配都是指精确匹配.
        
        a.前缀匹配:...where nike like 'asd%'。
            前缀匹配可使用索引,中缀和后缀匹配就只能全盘扫描了。
            
        b.范围匹配:...where a > 1 and a < 5 and b > 1;
            多个列同时进行范围匹配查找时,只针对最左边的那个列进行范围查找时用到了索引(B+树)
            
        c.精确匹配某一列并范围匹配另外一列
            select * from  table_name where a = 1 and b > 3;
            如果左边的列是精确查找,右边的列可以进行范围查找
            
        d.索引列使用函数后,索引当即失效
        
            比如常用日期相关函数:date()、datediff(date1,date2)、date_format(timestamp1,'%Y-%m-%d')等
            
            log_time为索引,查看某一天的玩家日志,以下5种方式中,只有2和3用到了索引
            1.explain select * from `player_log` where DATEDIFF(date(`log_time`),CURDATE()) = -1;
            2.explain select * from `player_log` where `log_time` BETWEEN '2020-11-04 00:00:00' AND '2020-11-05 00:00:00';
            3.explain select * from `player_log` where `log_time` >= '2020-11-04 00:00:00' and `log_time` < '2020-11-05 00:00:00';
            4.explain select * from `player_log` where DATE_FORMAT(log_time,'%Y-%m-%d') = '2020-11-04';
            5.explain select * from `player_log` where date(log_time) = '2020-11-04';
            
            优化方式:使用范围查询取代函数
            
    8.2 多列索引(覆盖索引)
        
        什么是覆盖索引?
        
        满足查询中给定表用到的所有列,包括where语句、order by语句、group by语句、以及select语句中的所有列
            ex: select a, b from table123 where c = 110 order by d desc; (index_all(c, d, a, b))
        
        注意:mysql通常一次查询只能使用一个索引,这是由B+树的结构决定的。而不是我们自以为的建两条单列的索引就能起到叠加的效果
        
        #step1.假设artist_id是主键,没有创建索引
        select artist_id, type, name from artist where type = 'Person';
        
        #step2.创建单列索引后,以上select语句速度显著提高。
        alter table artist add key index_type(type);
        
        #step3.创建多列索引(覆盖索引)后,以上select语句速度进一步提高。
        alter table artist add key index_type_name(type, name);
        
        说明:为何artist_id没有包括在覆盖索引内?
        innodb非主码索引特性:在innodb中,主码的值会被附加在非主码索引的每个对应记录后面,因此没有必要在非主码索引中指定主码。
        即,innodb引擎中所有非主码索引都隐含主码列了。
        
        #step4.添加多个索引,合并DML语句,提高效率(创建索引语句,非常耗时,并且会阻塞其他操作)
        alter table artist add index index_type(type), add index index_type_name(type, name);
        #分开成两条alter语句,在生产环境消耗的时间较多
        #创建index_type和index_type_name两个索引显然重复了,此处仅为了举例说明
        
    8.3索引覆盖where和order by语句
    
        建立一个同时满足 where语句 和 order by语句 的索引
        
    8.3 查看索引语句
        show index from table_abc;
        查看表当前创建的索引
        
    8.4 生产环境中创建索引考虑的因素
        
        a.alter是DDL语句,执行时会阻塞所有DML(查询/修改/添加)语句。
        b.如果表数据比较大,alter语句执行时间会比较长。
        c.一个表有多个索引情况下DML的性能开销。
        
        添加索引前至少做两项检查:
            a.验证表的现有结构  b.确定表的大小
    
    8.5 索引提高表连接查找效率
        在表连接的列上使用索引,可以显著提升性能
        
    8.6 不要再select查询中使用:select *
        因为如果在select语句中只包含那些真正需要的列,就能顺利通过创建合适的索引来获得更好的SQL优化。

你可能感兴趣的:(Mysql,mysql,索引,数据库)