许多基于位置的服务提供用于查找给定纬度经度对周围的场所/场地/点的API。我正在研究如何在整个城市搜索这些地方。
我可以通过从谷歌地图地理编码器获取界限,然后增加纬度/长度来放置点以形成网格,从而为城市构建网格。我prototyped this grid (点击“填充网格”按钮查看所有点)可视化这个想法。
// gather a collection of lat/long pairs that represents a grid of the city
var latIncrement = .04;
var lngIncrement = .04;
var newLat = nw.lat();
while(newLat >= sw.lat()) {
var newLng = nw.lng();
while(newLng <= ne.lng()) {
// western and northern border as well as grid infill
addMarker(new google.maps.LatLng(newLat, newLng));
newLng += lngIncrement;
}
// eastern border
addMarker(new google.maps.LatLng(newLat, ne.lng()));
newLat -= latIncrement;
}
// southern border
var newLng = sw.lng();
while(newLng <= se.lng()) {
addMarker(new google.maps.LatLng(sw.lat(), newLng));
newLng += lngIncrement;
}
addMarker(se);
然后,我可以根据LBS API获取所有这些要点并对其进行搜索。
我的问题是,是否有更科学的方法/算法来建立这个网格?我想更多地了解它们。我只是随意增加lat / lngs直到我到达网格的边界。地方的密度将根据城市和城市的面积而变化很大,因此有时增量太小,有时太大。我正在寻找关于如何更好地调整它的想法?
答案 0 :(得分:2)
可能更有效/更干净的方法是找到城市的bounding rectangle,这是一个矩形,每条边是城市边界点之间的极端基点,如果你能找到它们,然后迭代地填充它们。但无论如何,这基本上就是你已经在做的事情。
至于地点密度,您是否有一个特定的API,您将使用它?如果您在检测地点时知道API点数的“范围”,则您只需要将网格点与其半径尽可能接近。
话虽如此,您是否考虑过看看API是否直接支持在边框中搜索?这可能是你最好也是最干净的赌注。
在阅读你的评论后,这是一种可能效率低下的方式,我将来会考虑并改进,但它可能会帮助你开始。
在您所在城市的中心放置一个点,并观察检测到的所有位置。找到您所在位置的convex hull,并在凸包上的每个位置放置一个新点。然后,将所有位于这些新添加点范围内的位置添加到您的位置列表中。
然后,找到那些凸包,并重复相同的过程。
这实际上可能会减少人口稀少的城市的积分数量。对于密集的,它可能不是最佳的,但它可能会让你开始在工作轨道。
答案 1 :(得分:0)
虽然我遇到了同样的问题。我想出了一个解决方案,你将以自上而下的递归方式进行网格搜索。如果该API支持边界框搜索,这将起作用。最初假设您的城市为广场。现在使用该方块中的API获取数据/位置(边界框查询)。现在,如果返回的地点的数量超过某个阈值,则将城市广场分成4个相等的正方形,并为每个正方形重复该过程。如果返回的地点数量较少,请不要拆分。这将阻止网格搜索到非业务区域(正方形),如森林,河流等。这是原型python代码:
这里fetch是基于边界框从API获取结果的函数,其中sw为西南纬度,logitude元组和ne为东北纬度,逻辑元组
allresults = []
def grid_search(sw,ne):
global results
results = fetch(sw,ne)
if len(results) <= 10:
return
allresults.append(results)
swlat,swlon = sw
nelat,nelon = ne
grid_search( (swlat + delta, swlon), (nelat, sw + delta) )
grid_search( (swlat + delta, swlon + delta), ne )
grid_search( sw, (swlat + delta, swlon + delta) )
grid_search( (swlat,swlon + delta), (swlat + delta, nelon) )