首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >MySQL在explain语句中声明将使用我的索引时,并不使用我的索引

MySQL在explain语句中声明将使用我的索引时,并不使用我的索引
EN

Stack Overflow用户
提问于 2018-10-23 15:21:40
回答 1查看 46关注 0票数 0

我最近遇到了一个涉及MySQL DBSM的问题。

表如下所示:

代码语言:javascript
复制
 CREATE TABLE `orders` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(60) DEFAULT NULL,
`age` int(11) DEFAULT NULL,
`sex` enum('男','女') DEFAULT NULL,
`amount` float(10,2) DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `name_i` (`name`),
KEY `sex` (`sex`)
) ENGINE=InnoDB AUTO_INCREMENT=5000001 DEFAULT CHARSET=utf8 

如上所示,我在col name上创建了一个列索引

我想在name上执行一个范围查询,explain语句是

代码语言:javascript
复制
mysql> explain select * from orders where name like '王%';
+----+-------------+--------+------------+-------+---------------+--------+---------+------+-------+----------+----------------------------------+
| id | select_type | table  | partitions | type  | possible_keys | key    | key_len | ref  | rows  | filtered | Extra                            |
+----+-------------+--------+------------+-------+---------------+--------+---------+------+-------+----------+----------------------------------+
|  1 | SIMPLE      | orders | NULL       | range | name_i        | name_i | 183     | NULL | 20630 |   100.00 | Using index condition; Using MRR |
+----+-------------+--------+------------+-------+---------------+--------+---------+------+-------+----------+----------------------------------+
1 row in set, 1 warning (0.10 sec)

所以它应该使用索引name_i并在瞬间完成查询(我的同学花了0.07秒),然而,结果是这样的:

代码语言:javascript
复制
| 4998119 | 王缝   |   27 | 男   | 159.21 |
| 4998232 | 王求葬 |   19 | 男   | 335.65 |
| 4998397 | 王倘予 |   49 | 女   | 103.39 |
| 4998482 | 王厚   |   77 | 男   | 960.69 |
| 4998703 | 王啄淋 |   73 | 女   | 458.85 |
| 4999106 | 王般埋 |   70 | 女   | 700.98 |
| 4999359 | 王胆具 |   31 | 女   | 362.83 |
| 4999510 | 王铁脾 |   31 | 女   | 973.09 |
| 4999880 | 王战万 |   59 | 女   | 127.28 |
| 4999928 | 王忆   |   42 | 女   |  72.47 |
+---------+--------+------+------+--------+
11160 rows in set (3.43 sec)

而且它似乎根本不使用索引,因为数据是按主键id而不是列name排序的(此外,与0.07秒相比,它太慢了)。

有没有人也遇到过这个问题?

EN

回答 1

Stack Overflow用户

发布于 2018-10-25 10:23:29

  • 表中有多少百分比是“国王”(王)?如果大于20%,它将选择进行表扫描,而不是使用索引。(实际上,这可能会更快。)(根据注释,表的0.22%是Kings.)
  • EXPLAIN,查询的执行是两回事。虽然我不记得证明过这一点,但EXPLAIN可能会说一回事,但查询可能会以另一种方式工作。
  • ,表中有500万行吗?当你第一次运行它的时候,缓存是“冷的”吗?它必须从磁盘中获取11,160行?然后,第二次,所有的都在缓存中,那么快得多?
  • 表是按“字母”(或其他中文单词)的顺序加载的吗?如果是这样,很可能in和名称位于您正在使用的utf8_general_ci COLLATION的同一order?
  • Apparently中?也许它没有很好地对中文进行排序。(提供一个测试用例;我会做一些测试。)
  • 我不明白为什么它也提到了MRR.
  • I,,我被"1分32秒24秒“搞糊涂了。ORDER BY name应该进一步鼓励优化器使用INDEX(name)。你能打开“优化器跟踪”吗?

要真正查看它是否使用了索引,请执行以下操作:

代码语言:javascript
复制
FLUSH STATUS;
SELECT ...;
SHOW SESSION STATUS LIKE 'Handler%';

如果较大的数字看起来像表中的行数,那么它将执行表扫描。如果它们看起来更像11160,那么他们就使用了索引。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/52943298

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档