1、是否存在查询多余数据的情况
简单的开销指标:
响应时间
扫描的行数
返回的行数
解决方案:
使用索引覆盖扫描(需要的数据都来自索引)
该表库表结构
重构查询方式
2、重构查询方式
(1)切分查询
比如使用limit、通过时间节点变化
(2)分解关联查询
把复杂查询,拆分为几个简单查询
3、查询执行基础
(1)一次查询过程:
客户端发送一条查询给服务器
服务器检查查询缓存,如果命中,直接返回缓存中结果
服务器进行SQL解析,预处理,由优化器来生成对应的执行计划
MySQL根据优化器的执行计划,调用存储引擎的API进行查询
返回结果
(2)查询优化处理
1)语法解析和预处理:对语法规则进行验证和解析查询,生成一个对应的解析树;预处理进一步检测数的合法性
2)查询优化器:验证语句合法和预处理之后,将其转换为执行计划。MySQL使用基于成本的优化器,尝试预测一个查询使用某种计划的成本,然后选择其中成本最小的一 个。但是优化器很多时候选择的执行计划也不是最优,可能需要自己的处理(比如force某个索引的使用)
3)MySQL中关联查询的执行方式(笛卡尔积、需要利用临时表)
先在一个表中取出单条数据
然后循环到下一个表中取出匹配的行
根据各个表中匹配的行,返回查询中需要的数据
MySQL的执行计划:开始一直嵌套循环、回溯完成所有表的关联。(左侧深度优先的树)
4)利用stright_join,指定执行表的顺序
5)排序优化
4、MySQL查询优化器的局限性
(1)关联子查询
比对下三种方式的执行计划
前两种没有区别:
explain
select
*
from
books_book
where
id
in
(
select
book_id
from
books_book_authors)
explain
select
*
from
books_book
where
exists
(
select
book_id
from
books_book_authors
where
books_book.id
=
book_id)
基于内联的这个效率比较高,不用做
books_book
表的全表扫描
explain
select
*
from
books_book
inner
join
books_book_authors
on
books_book.id
=
books_book_authors.book_id
(2)最大值和最小值的优化
利用limit来代替min
查询性能优化
explain
select
min
(aId)
from
mobile_article_pv
where
articleId
>
3
explain
select
aId
from
mobile_article_pv
where
articleId
>
3
limit
1
因为在索引结构上,是按照顺序来进行存储的,所以可以直接用limit来获取