我有一个包含数百万条记录(14,000,000)的简单表格,对于一个简单的查询,它花费了太多时间“发送数据”.
桌子
CREATE TABLE IF NOT EXISTS details (
id int(11) NOT NULL,
date date NOT NULL,
time int(2) NOT NULL,
minutes_online decimal(5,0) NOT NULL,
minutes_playing decimal(5,0) NOT NULL,
minutes_chatting decimal(5,0) NOT NULL,
minutes_away decimal(5,0) NOT NULL
PRIMARY KEY (id,date,time)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_general_ci;
简单的查询
mysql> SELECT * FROM details WHERE id = 3014595;
说明
mysql> EXPLAIN SELECT * FROM details WHERE id = 3014595;
+----+-------------+-----------+------+---------------+---------+---------+-------+------+-------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-----------+------+---------------+---------+---------+-------+------+-------+
| 1 | SIMPLE | details | ref | PRIMARY | PRIMARY | 4 | const | 1482 | |
+----+-------------+-----------+------+---------------+---------+---------+-------+------+-------+
查询的配置文件
mysql> SHOW PROFILE FOR QUERY 1;
+--------------------------------+----------+
| Status | Duration |
+--------------------------------+----------+
| starting | 0.000024 |
| checking query cache for query | 0.000078 |
| checking permissions | 0.000014 |
| Opening tables | 0.000126 |
| System lock | 0.000011 |
| Table lock | 0.000030 |
| init | 0.000027 |
| optimizing | 0.000117 |
| statistics | 0.040077 |
| preparing | 0.000029 |
| executing | 0.000006 |
| Sending data | 7.536960 |
| end | 0.000013 |
| query end | 0.000004 |
| freeing items | 0.000037 |
| storing result in query cache | 0.000006 |
| logging slow query | 0.000003 |
| cleaning up | 0.000006 |
+--------------------------------+----------+
如您所见,SELECT语句使用索引并只读取1482行.然而,查询花了7.536960秒发送数据.这就像查询读取它需要的更多行.
这是一个简单的查询,只有7个字段(行平均59字节),没有花哨的功能.知道是什么导致这个吗?
注意:id是用户ID.每个用户每天每小时可能至少有一个条目.因此,id不是唯一的.
编辑:我有另一个具有相同结构和更多行(3400万)的表.如果我在这个较大的表上运行相同的查询,它会在不到1秒的时间内返回结果.
唯一的区别是较大的表不会获得与较小的表一样多的查询.
>查询数量是否可能减慢进程? MySQL缓存已启用.我还有CakePHP缓存查询以减少查询数量.
>保存表的文件是否可能已损坏或有什么问题?
更新
通过将数据层与Web层分离来解决该问题.数据层也在RAM上升级并在raid10上运行.
解决方法:
对于那些偶然发现这个问题并且想知道即使没有升级RAM的人,为什么发送数据的时间要长得多.这是因为发送数据实际上包括搜索要发送的数据的时间.
The thread is reading and processing rows for a SELECT statement, and sending data to the client. Because operations occurring during this state tend to perform large amounts of disk access (reads), it is often the longest-running state over the lifetime of a given query.
标签:performance,mysql
来源: https://codeday.me/bug/20190805/1591509.html