我有一个查询:
select SQL_NO_CACHE id from users
where id>1 and id <1000
and id in ( select owner_id from comments and content_type='Some_string');
(请注意,它缺少用于我的狮身人面像索引的实际大型查询,代表问题) 此查询大约需要3.5 秒(从 id = 1..5000 修改范围使其大约15 秒)。
users 表有大约 35000 个条目,comments 表有大约 8000 个条目。
解释上面的查询:
explain select SQL_NO_CACHE id from users
where id>1 and id <1000
and id in ( select distinct owner_id from d360_core_comments);
| 编号 | 选择类型 | 表| 类型 | 可能的键 | 关键 | key_len | 参考 | 行 | 额外 |
| 1 | 初级 | 用户 | 范围 | 初级 | 初级 | 4 | 空 | 1992 | 使用哪里;使用索引 || 2 | 依赖子查询 | d360_core_comments | 全部 | 空 | 空 | 空 | 空 | 6901 | 使用哪里;使用临时 |
这里的单个子查询(select owner_id from d360_core_comments where content_type='Community20::Topic';
)需要将近 0.0 秒。
但是,如果我在 owner_id,content_type 上添加索引,(请注意此处的顺序)
create index tmp_user on d360_core_comments (owner_id,content_type);
我的子查询在 ~0.0 秒内按原样运行,没有使用索引:
mysql> 解释 select owner_id from d360_core_comments where content_type='Community20::Topic';
| 编号 | 选择类型 | 表| 类型 | 可能的键 | 关键 | key_len | 参考 | 行 | 额外 |
| 1 | 简单 | d360_core_comments | 全部 | 空 | 空 | 空 | 空 | 6901 | 使用位置 |
然而,现在我的主要查询 ( select SQL_NO_CACHE id from users where id>1 and id <1000 and id in ( select owner_id from d360_core_comments where content_type='Community20::Topic');
) 现在在 ~0 秒内运行,解释如下:
mysql> 解释 select SQL_NO_CACHE id from users where id>1 and id <1000 and id in (select owner_id from d360_core_comments where content_type='Community20::Topic');
| 编号 | 选择类型 | 表| 类型 | 可能的键 | 关键 | key_len | 参考 | 行 | 额外 |
| 1 | 初级 | 用户 | 范围 | 初级 | 初级 | 4 | 空 | 1992 | 使用哪里;使用索引 || 2 | 依赖子查询 | d360_core_comments | 索引子查询 | tmp_user | tmp_user | 5 | 功能 | 34 | 使用位置 |
所以我的主要问题是:
- 如果在我的子查询中使用的表上定义的索引没有在我的实际子查询中使用,那么它如何在这里优化查询?
- 以及为什么当实际的子查询和主查询独立地更快时,第一个查询首先要花费这么多时间?