Chinaunix首页 | 论坛 | 博客
  • 博客访问: 2767082
  • 博文数量: 389
  • 博客积分: 4177
  • 博客等级: 上校
  • 技术积分: 4773
  • 用 户 组: 普通用户
  • 注册时间: 2008-11-16 23:29
文章分类

全部博文(389)

分类: Mysql/postgreSQL

2015-04-16 20:08:38

                                  MySQL使用索引的几种方式

      之前的blog有介绍令人迷糊的extra中信息,本文我们重点来看看当执行计划使用索引的时候
extra中几种显示的场景

 版本:Mysql 5.6.14

测试表结构如下:

 CREATE TABLE `snapshot` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `snap_id` int(11) DEFAULT NULL,
  `name` varchar(500) DEFAULT NULL,
  `value` int(11) DEFAULT NULL,
  PRIMARY KEY (`id`),
  KEY `snap_id_ix` (`snap_id`)
) ENGINE=InnoDB  DEFAULT CHARSET=utf8

在snap_id上创建了索引,然后插入一些测试数据。

1,snap_id为等于的操作

mysql> explain extended select * from snapshot where snap_id=10;
+----+-------------+----------+------+---------------+------------+---------+-------+------+----------+-------+
| id | select_type | table    | type | possible_keys | key        | key_len | ref   | rows | filtered | Extra |
+----+-------------+----------+------+---------------+------------+---------+-------+------+----------+-------+
|  1 | SIMPLE      | snapshot | ref  | snap_id_ix    | snap_id_ix | 5       | const |    1 |   100.00 | NULL  |
+----+-------------+----------+------+---------------+------------+---------+-------+------+----------+-------+
1 row in set, 1 warning (0.00 sec)

这个虽然使用了索引,但是extra中没有任何信息,显示为空


2,使用索引条件,先扫描索引,然后再通过索引扫描表

mysql>  explain extended select *  from snapshot where snap_id<100;
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+-----------------------+
| id | select_type | table    | type  | possible_keys | key        | key_len | ref  | rows | filtered | Extra                 |
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+-----------------------+
|  1 | SIMPLE      | snapshot | range | snap_id_ix    | snap_id_ix | 5       | NULL |    1 |   100.00 | Using index condition |
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+-----------------------+
1 row in set, 1 warning (0.00 sec)

通过索引条件,然后扫描表数据,extra是Using index condition

 

3,使用cover index,只查索引中的列,直接从索引中返回数据就可以了


mysql>  explain extended select snap_id from snapshot;
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+-------------+
| id | select_type | table    | type  | possible_keys | key        | key_len | ref  | rows | filtered | Extra       |
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+-------------+
|  1 | SIMPLE      | snapshot | index | NULL          | snap_id_ix | 5       | NULL | 6415 |   100.00 | Using index |
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+-------------+
1 row in set, 1 warning (0.00 sec)

mysql>  explain extended select snap_id from snapshot where snap_id=10;
+----+-------------+----------+------+---------------+------------+---------+-------+------+----------+-------------+
| id | select_type | table    | type | possible_keys | key        | key_len | ref   | rows | filtered | Extra       |
+----+-------------+----------+------+---------------+------------+---------+-------+------+----------+-------------+
|  1 | SIMPLE      | snapshot | ref  | snap_id_ix    | snap_id_ix | 5       | const |    1 |   100.00 | Using index |
+----+-------------+----------+------+---------------+------------+---------+-------+------+----------+-------------+
1 row in set, 1 warning (0.01 sec)

mysql>  explain extended select snap_id from snapshot where snap_id>10;
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+--------------------------+
| id | select_type | table    | type  | possible_keys | key        | key_len | ref  | rows | filtered | Extra                    |
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+--------------------------+
|  1 | SIMPLE      | snapshot | range | snap_id_ix    | snap_id_ix | 5       | NULL | 6367 |   100.00 | Using where; Using index |
+----+-------------+----------+-------+---------------+------------+---------+------+------+----------+--------------------------+
1 row in set, 1 warning (0.00 sec)

在extra出现的是Using index提示,表明只使用索引即可,不需要对表进行扫描操作.

 

4,   接下来我们看连接的操作,假设为snapshot作为连接的内表

mysql> explain
    -> select *
    -> from t1 join snapshot
    -> on (t1.a=snapshot.snap_id)
    -> ;
+----+-------------+----------+------+---------------+------------+---------+----------+------+-------+
| id | select_type | table    | type | possible_keys | key        | key_len | ref      | rows | Extra |
+----+-------------+----------+------+---------------+------------+---------+----------+------+-------+
|  1 | SIMPLE      | t1       | ALL  | PRIMARY       | NULL       | NULL    | NULL     |    3 | NULL  |
|  1 | SIMPLE      | snapshot | ref  | snap_id_ix    | snap_id_ix | 5       | db1.t1.a |  200 | NULL  |
+----+-------------+----------+------+---------------+------------+---------+----------+------+-------+
2 rows in set (0.00 sec)

通过执行计划可以看出对snapshot也是索引来访问的,外表传过来的值,在内表很类似于snap_id=XX,所以和第1中的执行
计划很类似.除ref之外,一个是来自于常量(const),而本例中是来自表t1的索引db.t1.a.


 

阅读(3168) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~