in 型子查询引出的陷阱
2015-12-09 13:52
435 查看
题: 在ecshop商城表中,查询6号栏目的商品, (注,6号是一个大栏目) 最直观的: mysql> select goods_id,cat_id,goods_name from goods where cat_id in (select cat_id from ecs_category where parent_id=6); 误区: 给我们的感觉是, 先查到内层的6号栏目的子栏目,如7,8,9,11 然后外层, cat_id in (7,8,9,11) 事实: 如下图, goods表全扫描, 并逐行与category表对照,看parent_id=6是否成立 原因: mysql的查询优化器,针对In型做优化,被改成了exists的执行效果. 当goods表越大时, 查询速度越慢. 改进: 用连接查询来代替子查询 explain select goods_id,g.cat_id,g.goods_name from goods as g inner join (select cat_id from ecs_category where parent_id=6) as t using(cat_id) \G 内层 select cat_id from ecs_category where parent_id=6 ; 用到Parent_id索引, 返回4行 +--------+ | cat_id | +--------+ | 7 | | 8 | | 9 | | 11 | +--------+ 形成结果,设为t *************************** 3. row *************************** id: 2 select_type: DERIVED table: ecs_category type: ref possible_keys: parent_id key: parent_id key_len: 2 ref: rows: 4 Extra: 3 rows in set (0.00 sec) 第2次查询, t和 goods 通过 cat_id 相连, 因为cat_id在 goods表中有索引, 所以相当于用7,8,911,快速匹配上 goods的行. *************************** 2. row *************************** id: 1 select_type: PRIMARY table: g type: ref possible_keys: cat_id key: cat_id key_len: 2 ref: t.cat_id rows: 6 Extra: 第1次查询 : 是把上面2次的中间结果,直接取回. *************************** 1. row *************************** id: 1 select_type: PRIMARY table: <derived2> type: ALL possible_keys: NULL key: NULL key_len: NULL ref: NULL rows: 4 Extra:
题: 在ecshop商城表中,查询6号栏目的商品, (注,6号是一个大栏目)
最直观的:
mysql> select goods_id,cat_id,goods_name from goods where cat_id in (select
cat_id from ecs_category where
parent_id=6);
误区: 给我们的感觉是, 先查到内层的6号栏目的子栏目,如7,8,9,11
然后外层, cat_id
in (7,8,9,11)
事实: 如下图, goods表全扫描, 并逐行与category表对照,看parent_id=6是否成立
![](file:///C:/Users/ADMINI~1/AppData/Local/Temp/msohtmlclip1/01/clip_image002.jpg)
原因: mysql的查询优化器,针对In型做优化,被改成了exists的执行效果.
当goods表越大时, 查询速度越慢.
改进: 用连接查询来代替子查询
explain select goods_id,g.cat_id,g.goods_name
from goods as g
inner
join (select cat_id from ecs_category where parent_id=6) as t
using(cat_id) \G
内层 select
cat_id from ecs_category where parent_id=6 ; 用到Parent_id索引, 返回4行
+--------+
| cat_id |
+--------+
|
7 |
|
8 |
|
9 |
|
11 |
+--------+ 形成结果,设为t
*************************** 3. row
***************************
id: 2
select_type: DERIVED
table: ecs_category
type: ref
possible_keys: parent_id
key: parent_id
key_len: 2
ref:
rows: 4
Extra:
3 rows in set (0.00 sec)
第2次查询,
t和 goods 通过 cat_id 相连,
因为cat_id在 goods表中有索引, 所以相当于用7,8,911,快速匹配上 goods的行.
*************************** 2. row
***************************
id: 1
select_type: PRIMARY
table: g
type: ref
possible_keys: cat_id
key: cat_id
key_len: 2
ref: t.cat_id
rows: 6
Extra:
第1次查询 :
是把上面2次的中间结果,直接取回.
*************************** 1. row
***************************
id: 1
select_type: PRIMARY
table: <derived2>
type: ALL
possible_keys: NULL
key: NULL
key_len: NULL
ref: NULL
rows: 4
Extra:
相关文章推荐
- 高端技巧:如何使用#define定义变量
- POJ 3468 线段树区间更新
- 高端技巧:如何使用#define定义变量
- python基础教程共60课-第12课for循环
- onNewIntent
- 湖南多校对抗赛(2015.03.28)
- mysql基础(五) Mysql删除表时,报"Connot delete or update a parent row:a foreign key constraint fails"解决方案
- Maven搭建SpringMVC+Hibernate项目详解
- 改变PS1的颜色
- HTTP状态码
- quarzy实现定时任务以及和spring整合
- linux的 压缩与解压 命令集
- 深入理解Java:SimpleDateFormat安全的时间格式化
- linux的 压缩与解压 命令集
- CSS中具有继承性的属性:
- Maven搭建SpringMVC+Hibernate项目详解
- iOS之旅--封装NavigationController
- zzulioj 1806: n个数的最小公倍数 (GCD)
- Microsoft Azure Tools: Failed to initialize Microsoft Azure storage emulator. The storage emulator n
- 格式化输出(printf,sprintf)