写了一个线上的功能,测试没有bug 上线了也可以正常运行,但是过了时间没多久,就出现一个问题 数据查询非常慢 三张表关联查询 一千多条数据 速度差不多4秒5秒
问题描述:
1.可以看出来1638条数据 查询数据库执行sql直接用时快3s的时间,这个一定有问题
首先来说下整理分析思路:
首先查看数据库的索引:
索引是创建了,而且索引类型和索引方法都没有问题,所以可以看出建表没有问题
首先执行 分析sql语句 explain select … from … [where …]
输出格式:
+----+-------------+-------+-------+-------------------+---------+---------+-------+------
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+-------+-------------------+---------+---------+-------+------
下面对各个属性进行了解:
1、id:这是SELECT的查询序列号
2、select_type:select_type就是select的类型,可以有以下几种:
SIMPLE:简单SELECT(不使用UNION或子查询等)
PRIMARY:最外面的SELECT
UNION:UNION中的第二个或后面的SELECT语句
DEPENDENT UNION:UNION中的第二个或后面的SELECT语句,取决于外面的查询
UNION RESULT:UNION的结果。
SUBQUERY:子查询中的第一个SELECT
DEPENDENT SUBQUERY:子查询中的第一个SELECT,取决于外面的查询
DERIVED:导出表的SELECT(FROM子句的子查询)
3、table:显示这一行的数据是关于哪张表的
4、type:这列最重要,显示了连接使用了哪种类别,有无使用索引,是使用Explain命令分析性能瓶颈的关键项之一。
结果值从好到坏依次是:
system > const > eq_ref > ref > fulltext > ref_or_null > index_merge > >unique_subquery > index_subquery > range > index > ALL
一般来说,得保证查询至少达到range级别,最好能达到ref,否则就可能会出现性能问题。
5、possible_keys:列指出MySQL能使用哪个索引在该表中找到行
6、key:显示MySQL实际决定使用的键(索引)。如果没有选择索引,键是NULL
7、key_len:显示MySQL决定使用的键长度。如果键是NULL,则长度为NULL。使>用的索引的长度。在不损失精确性的情况下,长度越短越好
8、ref:显示使用哪个列或常数与key一起从表中选择行。
9、rows:显示MySQL认为它执行查询时必须检查的行数。
10、Extra:包含MySQL解决查询的详细信息,也是关键参考项之一。
这是sql的分析结果:
可以完全看出分析结果 表 cubi 和 crc 两个表的索引没有用上,上面看到表的索引创建都是没有问题的,那问题出现在哪?
在分析,如果建表和sql查询语句没有问题 那我只能想到建表的是时候字段的问题
打开表看了下,猜测会不会是字符集的问题,然后把字符集的字段修改了字符集为UTF-8然后分析表结果:
真的是没有让我失望,其实很多时候我们在建表的时候都是遵循者空间换时间的规则总是忽视了其他的问题,最后总结了下自己,遇到问题一步一步的分析结果,肯定能解决