- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我有两张 table
Sensorlist
id (int, PK)
alias (varchar)
Readings
sensorid (int)
value (decimal)
date (datetime)
id (bigint, PK)
读数表在 id、sensorid 和日期上有一个索引。这是在 MYSQL 中,在树莓派上运行。
我想获得一个列表,显示列表中的每个传感器,以及它们最近的读数以及过去 24 小时内的最小和最大读数。
我将以下两个查询拼凑成一个数组并显示。我不太清楚如何将两者作为一个查询来执行。第一个查询非常慢。我怎样才能让它更有效率?
获取最新读数需要 27 秒:
select distinct s.alias, s.id, a.maxdate, r.value from sensorlist s
inner join
(
SELECT MAX(date) maxDate, sensorid FROM readings GROUP BY sensorid
) a on a.sensorid = s.id
inner join readings r on r.sensorid = s.id and r.date = a.maxdate
ORDER BY s.alias
查询 2 获取最近 24 小时内的最小/最大值,这只需要 0.3 秒:
select distinct s.alias, s.id, max(value) as maxval, min(value) as minval from sensorlist s
inner join readings r on r.sensorid = s.id where r.date > DATE_SUB(NOW(), INTERVAL 24 HOUR) group by r.sensorid
我假设这是我完成子查询连接的方式..但我无法弄清楚如何不使用子查询,或者如何在一个查询中完成整个事情(如果那是一个更多有效路线?)
感谢您的任何建议,查理
编辑-完成的查询(如下面的答案所示,但 MYSQL 不喜欢“minvalue”这个词,根据答案添加了索引)
SELECT sensorlist.id, sensorlist.alias, a.maxval, a.minval, b.value AS lastvalue, b.date as recentdate
FROM (
SELECT sensorid, MAX(value) AS maxval, MIN(value) AS minval
FROM readings
WHERE date >= NOW() - INTERVAL 24 HOUR
GROUP BY sensorid
) AS a
JOIN (
select value, sensorid, date
FROM readings
JOIN
(
SELECT MAX(id) id FROM readings GROUP BY sensorid
) as m on m.id = readings.id
)
AS b ON a.sensorid = b.sensorid
JOIN sensorlist ON sensorlist.id = a.sensorid
非常感谢!
最佳答案
此查询获取最近 24 小时内每个传感器的最大和最小读数。注意没有任何 DISTINCT
指令; GROUP BY
会为您完成。
SELECT sensorid, MAX(value) AS maxvalue, MIN(value) AS minvalue
FROM readings
WHERE date >= NOW() - INTERVAL 24 HOUR
GROUP BY sensorid
如果您在 readings
表上创建以下复合索引,此查询很可能会获得很大的性能提升:(date,sensorid,value)
。这称为覆盖索引,您可以在您最喜欢的搜索引擎上查找它。它让 MySQL 使用随机访问准确地跳转到索引中的正确位置,然后按顺序扫描该索引以查找它需要的信息。可以从该索引满足整个查询。
现在,让我们添加 latest-measurement 要求。查找每个传感器的最新测量值的最简单方法是使用此子查询。我假设您的主键 readings.id
是一个自动增量字段。
SELECT MAX(id) id, sensorid FROM sensors GROUP BY sensorid
该查询为您提供了 readings
表中的 id
值列表。这些是每个不同传感器的最新读数的 id
值。要优化它,您可以在 (sensorid, id)
上创建另一个覆盖索引。
现在我们可以将该子查询加入查询的其余部分,并使用这些 ID 来查找最新值。请注意,我们最终得到两个不同的子查询。这是必要的,因为我们需要两种不同的聚合,根据不同的标准进行聚合。我们还将加入传感器别名以供显示。
SELECT sensorlist.id, sensorlist.alias, a.maxvalue, a.minvalue, b.value AS lastvalue
FROM (
SELECT sensorid, MAX(value) AS maxvalue, MIN(value) AS minvalue
FROM readings
WHERE date >= NOW() - INTERVAL 24 HOUR
GROUP BY sensorid
) AS a
JOIN (
SELECT value, sensorid
FROM sensors
JOIN (
SELECT MAX(id) id FROM sensors GROUP BY sensorid
) AS m ON sensors.id = m.id
) AS b ON a.sensorid = b.sensorid
JOIN sensorlist ON sensorlist.id = a.sensorid
使此性能良好的技巧是通过使用适当的索引来优化命中读数表的两个子查询。
最后,您可以测试这个结合了两个聚合器查询的查询,看看它是否更快。
SELECT sensorlist.id, sensorlist.alias, a.maxvalue, a.minvalue, b.value AS lastvalue
FROM (
SELECT sensorid, MAX(value) AS maxvalue, MIN(value) AS minvalue,
MAX(id) AS maxid
FROM readings
WHERE date >= NOW() - INTERVAL 24 HOUR
GROUP BY sensorid
) AS a
JOIN readings AS b on b.id = a.maxid
JOIN sensorlist ON sensorlist.id = a.sensorid
关于mysql - 优化 SQL 查询-传感器读数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27693816/
我在将一些 C++ 代码转换为 Arduino 时遇到问题。任何帮助,将不胜感激。 编辑 我已经成功完成了上述操作。然而,现在唯一的问题是我的 Arduino 代码准确而正确地读取了电压,但没有其他寄
我需要能够从 HealthKit 读取所有 HRV 读数,并根据它们的创建日期对它们的值进行排序。 我可以使用 SampleQuery 从 HealthKit 读取特定时间间隔内的所有读数,如下所示:
我正在尝试使用 arduino uno R3 从 DHT-11 传感器读取温度和湿度 #include #include #define DHTPIN A3 #define DHTTYPE DHT
伙计们,我是 Meteor 的新手。对于我目前的应用程序,我正在使用 openlayer,因此对于 openlayer,我调用 Template.map.onRendered 事件,该事件将加载一个
我有一个设备可以读取电气设备的 kw 值,以测量它们在特定时间的(能量消耗率)。然后将这些值发送到轮询器(它定期向设备询问这些值),并插入到数据库中。 例子: 1st reading - 10 kw
我是一名优秀的程序员,十分优秀!