#查看是否支持
select @@have_profilling;
#默认是关闭的
select @@profilling;
#通过set在当前级别开启
set profiling = 1;
# 执行完sql通过这条命令查看
show profiles;
# 根据 show profiles 获取到的哦 query_ID进一步查看详细信息
show profile for query 1;
-
analyze table lh_admin
本语句用于分析和存储表的关键字分布,分析的结果将可以使得系统得准确的统计信息,使得SQL能够生成正确的执行计划。如果用户感觉实际执行计划并不是预期的执行计划,执行一次分析表可能会解决问题。在分析期间,使用一个读取锁定对表进行锁定。对于 MyISAM,BDB,InnoDB表有作用。
-
check table lh_admin
检查表的作用是检查一个或多个表是否有错误。
可以检查视图是否有错误。
-
optimize table lh_admin
如果已经删除了表的一大部分,或者如果已经对含有可变长度行的表(含有 varchar,blob,text)进行了很多更改,则应使用
optimize table
命令来进行表优化。
-
是否向数据库请求了不需要的数据
-
查询不需要的记录。
一个常见的错误时常常会误以为MySQL会返回需要的数据,实际上MySQL却是先返回全部结果集再进行计算。
-
多表关联时返回全部列
-
总是取出全部列。(select * )
-
重复查询相同的数据。
例如,在用户评论的地方需要查询用户头像的URL,那么用户多次评论的时候,可能就会反复查询这个数据。比较好的方案是,当初次查询的时候将这个数据缓存起来,需要的时候从缓存中取出。
-
-
是否扫描额外的记录
- 对于MySQL,最简单的衡量查询开销的三个指标 : 响应时间,扫描的函数,返回的行数。
- 响应时间 : 服务时间加上排队时间。
- 扫描的行数和返回的行数
- 扫描的行数和访问的类型(explain type)
- MySQL能够使用如下三种方式应用where条件。从好到坏依次为
- 在索引中使用where条件来过滤不匹配的记录。这是在存储引擎成完成的。
- 使用索引覆盖扫描(在extra列中出现了using index)来返回记录,直接从索引中过滤不需要的记录并返回命中的结果。这是在MySQL服务器成完成的,但无须再回表查询记录。
- 从数据表中返回数据,然后过了不满足条件的记录(在 extra 列中出现 using where )。这在MySQL服务器层完成,MySQL需要先从数据库读出记录然后过滤。
-
一个复杂的查询还是多个简单查询
-
切分查询
例子,定期地清除大量数据时,如果用一个大的语句一次性完成的话,则可能需啊哟一次锁住很多数据、占满整个事务日志、耗尽系统资源、阻塞很多小的但重要的查询,同时还可以减少MySQL复制的延迟。
-
分解关联查询优势
- 让缓存的效率更高。许多应用程序可以方便地缓存单表查询对应的结果对象。
- 将查询分解后,执行单个查询可以减少锁的竞争。
- 在应用层做关联,可以更容易对数据库进行拆分,更容易做到高性能和可扩展。
- 可以减少冗余记录的查询。这样的重构还可以减少网络和内存的消耗。
- 当向MySQL发送一个请求的时候,MySQL做的事情
-
MySQL 客户端 / 服务器通信协议
- MySQL客户端和服务器之间的通信协议是 “半双工”的,意味着在任何一个时刻,要么是由服务器向客户端发送数据,要么是由客户端向服务器发送数据,这两个动作不能同时发生。
- 客户端用一个单独的数据包将查询传给服务器。
max_allowed_packet
这个参数配置。
-
查询状态
-
对于一个MySQL连接,任何时刻都有一个状态,
show full processlist
-
sleep 线程正在等待客户端发送新的请求。
-
query 线程正在执行查询或者正在将结果发送给客户端。
-
locked
在MySQL服务层,该线程正在等待表锁。在存储引擎级别实现的锁,例如InnoDB的行锁,并不会体现在线程状态中。
-
analyzing and statistics
线程正在收集存储引擎的统计信息,并生成查询执行计划。
-
copying to tmp table
线程正在执行查询,并且将其结果都复制到一个临时表中,这种状态一般要么是在做
group by
操作。要么是文件排序操作,或者是union
操作。 -
sorting result 线程正在对结果集进行排序。
-
sending data
这表示多种情况:线程可能在多个状态之间传送数据,或者在生产结果集,或者在向客户端返回数据。
-
-
查询缓存
-
查询优化处理
- 语法解析器和预处理
- 查询优化器
-
最大值和最小值优化。
#原理语句 select min(actor_id) from actor where first_name = 'penelope'; #优化 select actor_id from actor use index(primary) where firsh_name = 'penelope' limit 1;
-
优化COUNT() 查询
统计结果集的行数。当MySQL确认括号内的表达式值不可能为空时,实际上就是在统计行数。这样性能更好。
select count(*) from world.city where id > 5; #优化 select (select count(*) from world。city) -count (*) from world.city where id <= 5;
-
优化关联查询
- 确保任何的 group by 和 order by 中的表达式只涉及到一个表中的列。
- 确保 on 或者 using 子句中的列上有索引。
-
优化 limit 分页
-
利用
position between A and B order by position
-
利用 延迟关联
SELECT * FROM tbl_users JOIN ( SELECT id FROM tbl_users ORDER BY id DESC LIMIT 10000,5 ) as c using(id);
-
利用 where
select * from tbl_users where id > 100000 limit 20
-
-
优化 UNION 查询
MySQL总是通过创建并填充临时表的方式来执行 UNION 查询,经常需要手工地将 where ,limit,order by 等子句 “下推” 到UNION 的各个子查询中。
#统计一个表中不同类型的总数。
select sum(if(color = 'blue',1,0)) as blue,sum(if(color = 'red',1,0)) as red from items;