MySQL选择查询以扩大表优化

时间:2017-07-15 01:41:02

标签: php mysql query-optimization

我有一个MySQL表,其配置如下:

CREATE TABLE `MONITORING` (  
`REC_ID` int(20) NOT NULL AUTO_INCREMENT,  
`TIME` int(11) NOT NULL,  
`DEVICE_ID` varchar(30) COLLATE utf8_unicode_ci NOT NULL,  
`MON_ID` varchar(10) COLLATE utf8_unicode_ci NOT NULL,  
`TEMPERATURE` float NOT NULL,  
`HUMIDITY` float NOT NULL,  
PRIMARY KEY (`REC_ID`),  
KEY `SelectQueryIndex` (`TIME`,`MON_ID`))  
ENGINE=MyISAM AUTO_INCREMENT=102069 DEFAULT CHARSET=utf8  
COLLATE=utf8_unicode_ci 

多个监控设备始终准确地发送数据,但并非所有监控器始终在线。我使用PHP查询数据库并格式化数据以放入Google折线图。

要将数据导入Google图表,我运行的是一个SELECT查询,它会在一行中显示所有MON_ID的结果。

我目前使用的查询是:

SELECT `TIME`, `H5-C-T`, `P-C-T`, `H5-C-H`, `P-C-H`, `A-T`, `A-H` FROM
    (SELECT `TIME`, `TEMPERATURE` as 'H5-C-T', `HUMIDITY` as 'H5-C-H' FROM `MONITORING` where `MON_ID` = 'H5-C') AS TAB_1,
    (SELECT `TIME` as `TIME2`, `TEMPERATURE` as 'P-C-T', `HUMIDITY` as 'P-C-H' FROM `MONITORING` where `MON_ID` = 'P-C') AS TAB_2,
    (SELECT `TIME` as `TIME3`, `TEMPERATURE` as 'A-T', `HUMIDITY` as 'A-H' FROM `MONITORING` where `MON_ID` = 'Ambient') AS TAB_3
    WHERE TAB_1.TIME = TAB_2.TIME2 AND TAB_1.TIME = TAB_3.TIME3

结果正是我想要的(带有TIME的表,然后是三个监视器中每个监视器的Temp和RH列),但看起来查询花费的时间比给出结果要长很多。

打开整个表格,或选择一个监控设备的所有行大约需要0.0006秒(不能要求比这更好)。

如果我使用2个监控设备进行查询,则需要大约0.09秒(仍然不错,但增加的百分比相当大)。

当我放入第三个监控设备时,查询上升到大约2.5秒(现在没问题,但是随着收集的数据越来越多,并且更多的设备最终需要一次进入图表,它会继续快点过快了。)

我看了很多人们试图优化他们的查询的帖子,但找不到任何与我一样的查询(也许我这样做的方式很糟糕......)。从人们为提高性能所做的其他事情我已经尝试了多种索引方法,确保在PHP MyAdmin中检查,分析和优化表,尝试了几种其他查询方法,更改了表的排序字段/顺序等等但是还没有找到另一种方法来获得我需要的结果,这是更快的。

我的表总共有不到10万行,看起来我的查询速度比根据我看到对有数千万条记录的表进行查询的许多人所预期的要长。 / p>

有关优化查询的方法的任何建议吗?

也许答案就像是多个MySQL查询,然后以某种方式在PHP中将它们合并在一起(我试图找到一种方法来实现这一点,但无法让它工作)?

1 个答案:

答案 0 :(得分:0)

把东西翻过来;表现会好很多:

SELECT  h.`TIME`,
        h.TEMPERATURE AS 'H5-C-T',
        p.TEMPERATURE AS 'P-C-T',
        h.HUMIDITY AS 'H5-C-H',
        p.HUMIDITY AS 'P-C-H', 
        a.TEMPERATURE AS 'A-T', 
        a.HUMIDITY AS 'A-H'
    FROM MONITORING AS h
    JOIN MONITORING AS p ON h.TIME = p.TIME
    JOIN MONITORING AS a ON a.TIME = h.TIME
    WHERE h.`MON_ID` = 'H5-C'
      AND p.`MON_ID` = 'P-C'
      AND a.`MON_ID` = 'Ambient'

并使用JOIN...ON语法。

TIME和REC_ID的组合是唯一的吗?如果是这样,如果您切换到InnoDB,摆脱REC_ID并将KEY SelectQueryIndex (TIME,MON_ID)更改为PRIMARY KEY(TIME, MON_ID),性能会更好。

您还应该考虑切换到InnoDB。