我试图实现类似于这里的谷歌商店定位器,但与车辆的GPS事件,所以每辆车有多个事件。此数据在EventData表中。
这是表格&为了方便起见,一些示例数据-时间戳被生成到现在,并有轻微的不同:
deviceID|timestamp |longitude|latitude|
1 |1323777977|73.52 | 18.55 |
2 |1323777973|73.52 | 18.55 |
1 |1323777833|73.52 | 18.55 |
1 |1323778111|73.52 | 18.55 |
3 |1323777912|73.52 | 18.55 |
2 |1323777922|73.52 | 18.55 |
3 |1323777971|73.52 | 18.55 |
3 |1323777831|73.52 | 18.55 |
1 |1323777957|73.52 | 18.55 |
1 |1323778111|73.52 | 18.55 |
下面是查询:
SELECT DISTINCT(`EventData`.`deviceID`),`EventData`.`timestamp`,`EventData`.`latitude`, `EventData`.`longitude`,
(6371 * acos( cos( radians(18.52) ) * cos( radians( `EventData`.`latitude` ) ) * cos( radians( `EventData`.`longitude` ) - radians(73.58) ) + sin( radians(18.52) ) * sin( radians( `EventData`.`latitude` ) ) ) )
AS distance FROM `EventData` AS `EventData`
WHERE `EventData`.`timestamp` >= UNIX_TIMESTAMP(date_sub(now(), INTERVAL 6 day)) AND `EventData`.`timestamp` <= UNIX_TIMESTAMP(now()) AND `EventData`.`accountID` = 'sysadmin'
GROUP BY `EventData`.`deviceID`
HAVING distance < 5
ORDER BY `EventData`.`timestamp` DESC;
我想要得到的是最近的车辆(小于5公里或10英里)到lat/lat 18.52, 73.58,因为会有多个这样的条目,按EventData.deviceID(其唯一ID)分组,最后按时间戳排序,以获得每个设备的最新记录。我使用这个section是因为这个表已经有了索引&使用此函数还可以大大加快响应速度:
AND `EventData`.`accountID` = 'sysadmin'
显然我做了一些非常错误的事情,因为选择了唯一的车辆,但它们的时间戳意味着它们既不是最早的记录,也不是最新的记录。我是一个MySQL菜鸟,请不要评判!
http://code.google.com/apis/maps/articles/phpsqlsearch.html
是Google的商店定位器示例,但具有唯一的商店记录。
尝试按
排序ORDER BY MAX(`EventData`.`timestamp`) DESC;
我的问题解决了。
在SELECT语句中,我使用(感谢@symcbean):
MAX(`EventData`.`timestamp`)
这消除了使用Order By子句的需要(它无论如何都不起作用)。然而,查询仍然很慢,执行时间超过500ms,同时消耗了大量CPU。因此,我在PHP中计算了当前时间戳和6天前的时间戳,然后执行查询,瞧!仅200毫秒和最佳的CPU使用率!
Acc。对于EXPLAIN数据输出,它使用一个临时表&
这个链接可能有助于获得更优化的查询与"内连接"等,但我不确定如何!http://kristiannielsen.livejournal.com/6745.html