`
丁林.tb
  • 浏览: 796714 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

MySQL优化器中一个Count和覆盖索引的问题

阅读更多

    前天在微薄上发了个优化器的问题,从评论来看,还是需要简单说明一下。

 

explain.jpg

 

现象说明

       其实这里主要要说明的是一个优化器还需要改进的地方。

 

优化器会根据where条件和select_list里面的字段决定在使用一个索引(sta)后,是否需要回表回到聚集索引取数据。

 

基本的做法是:在确定了一个索引后,将select_listwhere中出现的所有字段都拿来判断一下,如果字段都存在于sta索引中,则可以使用覆盖索引。

 

第一个explan可以用上覆盖索引(Using Index), 是因为select_list里面只有count(*),而count(*)在语法解析阶段就被特殊处理,不作为特殊字段。

 

第二个字段在现在的实现中,因为gmt不是sta索引的一部分(sta索引定义上只有sta一个字段,算上聚集索引结构,就是sta,auci)。所以最后判定为不能使用覆盖索引。

 

性能差别

         表中放入500w数据以后,这两个查询的时间相差25(0.19s vs  5s)

 

存在改进

         其实我说这个“不科学”,是因为第二个语句居然不能使用覆盖索引。按照count(gmt)的语义,是计算gmt不为NULL的所有行的数目。但是表定义中,分分明已经说明了gmtnot null。那么就可以转成count(*)了!

     目前因为count、sum、count(distinct)这些操作的处理方法被揉在一起,因此没有特别分开。

 

应用警惕

         好在按照正常的习惯,需要计算总数时,最多是count(auci)或者count(*) 不会故意去count一个别的字段。当时若使用的是MyISAM,就需要小心了。

 

         从上面的分析可以推测得到,如果这是个MyISAM表,还是一样的where条件,count(*)是可以使用覆盖索引的,但是count(auci)就不行了。

  • 大小: 189.7 KB
  • 大小: 160.8 KB
0
3
分享到:
评论
1 楼 zhoujy 2013-05-20  
root@192.168.200.202 : test 11:44:37>show create table my_data\G;
*************************** 1. row ***************************
       Table: my_data
Create Table: CREATE TABLE `my_data` (
  `auci` int(11) NOT NULL,
  `tit` varchar(256) DEFAULT NULL,
  `gmt` datetime DEFAULT NULL,
  `sta` datetime DEFAULT NULL,
  `pic` varchar(256) DEFAULT NULL,
  PRIMARY KEY (`auci`),
  KEY `sta` (`sta`),
  KEY `idx_gmt` (`gmt`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
1 row in set (0.00 sec)

ERROR: 
No query specified

root@192.168.200.202 : test 11:47:26>explain select count(*) from my_data where sta>='2011-05-20';
+----+-------------+---------+-------+---------------+------+---------+------+------+--------------------------+
| id | select_type | table   | type  | possible_keys | key  | key_len | ref  | rows | Extra                    |
+----+-------------+---------+-------+---------------+------+---------+------+------+--------------------------+
|  1 | SIMPLE      | my_data | index | sta           | sta  | 6       | NULL |    2 | Using where; Using index |
+----+-------------+---------+-------+---------------+------+---------+------+------+--------------------------+
1 row in set (0.00 sec)

root@192.168.200.202 : test 11:47:43>explain select count(gmt) from my_data where sta>='2011-05-20';
+----+-------------+---------+-------+---------------+------+---------+------+------+-----------------------+
| id | select_type | table   | type  | possible_keys | key  | key_len | ref  | rows | Extra                 |
+----+-------------+---------+-------+---------------+------+---------+------+------+-----------------------+
|  1 | SIMPLE      | my_data | range | sta           | sta  | 6       | NULL |    2 | Using index condition |
+----+-------------+---------+-------+---------------+------+---------+------+------+-----------------------+
1 row in set (0.00 sec)

root@192.168.200.202 : test 11:47:52>insert into my_data values(3,'asdasdasda',NULL,now(),'SDFSDF');
Query OK, 1 row affected (0.00 sec)

root@192.168.200.202 : test 11:48:02>explain select count(gmt) from my_data where sta>='2011-05-20';
+----+-------------+---------+------+---------------+------+---------+------+------+-------------+
| id | select_type | table   | type | possible_keys | key  | key_len | ref  | rows | Extra       |
+----+-------------+---------+------+---------------+------+---------+------+------+-------------+
|  1 | SIMPLE      | my_data | ALL  | sta           | NULL | NULL    | NULL |    3 | Using where |
+----+-------------+---------+------+---------------+------+---------+------+------+-------------+
1 row in set (0.00 sec)

相关推荐

    MySQL之高效覆盖索引

    覆盖索引(Covering Index)是数据库索引的一种优化技术,在MySQL等关系型数据库管理系统中被广泛应用。覆盖索引的特点在于它能够使得数据库系统在执行查询时,仅通过访问索引来获取所需的数据,而无需再访问实际的...

    分析MySQL中优化distinct的技巧

    MySQL的优化器将`DISTINCT`操作转换为`GROUP BY`,使得查询在利用索引分组后,仅扫描一次所需的`nick`值。在新的执行计划中,`Using index for group-by`表明查询利用索引完成了分组操作,从而提高了效率。 通过...

    MySQL索引优化课件

    本课件主要聚焦于MySQL数据库的索引原理、优化策略以及相关存储过程和触发器的应用。 首先,我们要理解什么是索引。索引就像书的目录,它为数据库中的数据提供快速访问的途径。在MySQL中,常见的索引类型有B-Tree...

    04-VIP-Mysql索引优化实战一.pdf

    MySQL索引优化是数据库性能提升的关键环节,本篇主要探讨了几个关于MySQL索引使用和优化的重要知识点。 首先,创建了一个名为`employees`的员工记录表,其中包含`id`(主键)、`name`、`age`、`position`和`hire_...

    mysql优化笔记+资料

    以下是一份详细的MySQL优化笔记,涵盖了多个方面: 一、查询优化 1. 使用索引:为经常用于搜索的列创建索引可以显著加快查询速度。B树和哈希索引是最常见的类型,适用于不同的查询场景。 2. 避免全表扫描:尽量使用...

    mysql-常见问题,索引优化

    为优化此操作,可以尝试创建一个覆盖列的唯一索引,或者在适当的情况下使用`GROUP BY`代替`COUNT(DISTINCT)`。 2. MySQL Sending data 导致查询很慢 当查询涉及大量数据传输时,`Sending data`状态可能持续很长时间...

    mysql的索引优化

    ### MySQL的索引优化 ...通过上述内容可以看出,合理使用和优化MySQL索引对于提升数据库性能至关重要。开发者应该根据具体的应用场景来选择合适的索引策略,并定期评估和调整索引设置,以确保系统的高效运行。

    mysql查询优化之索引优化

    总之,索引优化是提升MySQL查询性能的核心手段,需要结合业务需求和查询模式,进行细致的分析和调整。通过以上策略的实施,可以显著减少查询时间,提升数据库系统的整体效率。在实际工作中,不断学习和实践,掌握...

    MySQL数据库优化SQL篇PPT课件.pptx

    从执行计划、SELECT语句、IN和EXIST语句、LIMIT语句、RAND函数、Order by、Group by、Distinct和Count等方面对MySQL数据库优化进行了详细的讲解。 一、执行计划 执行计划是MySQL数据库优化的重要步骤。执行计划...

    MySQL数据库索引优化

    索引是数据库中一种非常重要的数据结构,它能够大幅提升查询的效率,但也需要恰当的管理和优化,以避免性能问题。 首先,BTree索引和Hash索引是两种最常见的索引类型。BTree索引适用于全值匹配、匹配最左前缀、匹配...

    MySql优化.rar

    在"MySQL优化.rar"这个压缩包中,我们很显然会接触到关于MySQL数据库优化的详细内容,这包括但不限于查询优化、索引优化、存储引擎选择、架构设计等多个方面。 首先,查询优化是MySQL性能提升的关键步骤。通过对SQL...

    mysql基础知识和mysql优化整理

    2. 索引优化:创建合适的索引,考虑使用覆盖索引,避免过多的索引,定期分析和优化索引。 3. 表设计优化:适当字段类型选择,避免NULL字段,合理拆分大表,使用分区表和分片技术。 4. 内存配置:调整缓冲池大小,...

    MySQL索引分析和优化.pdf

    ### MySQL索引分析和优化 #### 一、索引的重要性及原理 索引在数据库管理中扮演着极其重要的角色,特别是在提高数据检索速度方面。**MySQL索引**本质上是用来加快数据检索过程的一种数据结构,类似于书籍中的目录...

    mysql优化sql语句的优化(索引,常用小技巧.)

    ### MySQL优化之SQL语句与索引优化 #### 数据库设计合理性 在MySQL数据库的优化过程中,合理设计数据库(表)至关重要。一个合理的数据库设计能够有效地提高查询性能、减少数据冗余并确保数据完整性。 - **3NF**...

    MYSQL优化-一篇很好的优化文章

    10. 编译和安装MYSQL 11. 维护 12. 优化SQL 13. 不同SQL服务器的速度差别(以秒计) 14. 重要的MYSQL启动选项 15. 优化表 16. MYSQL如何次存储数据 17. MYSQL表类型 18. MYSQL行类型(专指IASM/MYIASM表) ...

    MySQL索引分析和优化[定义].pdf

    5. **单列索引**和**多列索引**的区别在于索引覆盖的列数。单列索引只针对一列,而多列索引可以包括两列或更多列。多列索引有助于优化涉及多个列的查询,因为数据库系统可以同时考虑多个列的索引结构。例如,对于一...

    MySql优化.pdf

    MySQL优化 MySQL优化是数据库管理中的一个重要...总结而言,MySQL优化是一个涉及多个层面的复杂过程,需要综合考虑配置、索引、查询语句、服务器状态等多方面因素,通过合理配置和优化,以达到提升数据库性能的目的。

Global site tag (gtag.js) - Google Analytics