AWS SimpleDB上的空间查询

use*_*895 6 spatial-query amazon-web-services amazon-simpledb

我想知道人们建议什么是在Amazon Web Services SimpleDB中进行空间查询的有效方法?

通过空间查询,我的意思是在纬度和经度的给定半径内找到对象.

Mar*_*son 14

SimpleDB目前不提供任何内置的空间搜索操作,但这并不意味着无法完成.有几种在非地理空间感知数据库(如SimpleDB)中实现地理空间搜索的方法,所有这些方法都围绕着使用数据库根据地理空间边界框检索粗略的第一选择,然后使用应用程序过滤返回的数据的想法.更精确的算法,如Haversine公式.

可以将纬度和经度存储为(零填充和规范化)数字属性,然后执行双范围查询(lat >= minLat and lat <= maxLat and lon >= minLat and lon <= maxLat)但由于这两个谓词都不是选择性的(每个谓词与许多项匹配),因此它不理想(请参阅调整查询).

更好的方法是使用GeoHashes.

Geohashes提供诸如任意精度,附近位置的类似前缀以及逐渐从代码末尾删除字符以减小其大小(并逐渐失去精度)的属性.

作为一个实际例子,Geohash 6gkzwgjzn820解码为坐标-25.382708和-49.265506,而Geohash 6gkzwgjz将解码为-25.383和-49.266,如果我们在相同区域采取类似位置,例如-25.427和-49.315 ,我们可以看到它被编码为6gkzmg1w(注意类似的前缀).

来自http://geohash.org/site/tips.html

与您的项目位置为GeoHashes你可以使用like操作符来搜索边界框(where GeoHash like '6gkzmg1w%'),但由于like运营商是昂贵(比较运算符)一个更好的方式是通过存储每个地理散列前缀级非规范化的数据(多少取决于你需要搜索精度)作为一个单独的属性(GeoHash6 GeoHash8等),然后使用一个简单的等式谓词(where Geohash8 = '6gkzmg1w').

现在是GeoHashes的缺点.由于您无法假设GeoHash在搜索框中居中,因此您还必须搜索所有相邻的前缀.geohash-js极好地描述了这个过程

Geohash还具有以下特性:随着位数的减少(从右侧开始),精度会降低.此属性可用于进行边界框搜索,因为彼此靠近的点将共享类似的Geohash前缀.

但是,因为给定点可能出现在给定Geohash边界框的边缘,所以有必要生成Geohash值列表,以便在点周围执行真正的邻近搜索.由于Geohash算法使用base-32编号系统,因此可以使用简单的查找表导出围绕任何其他给定Geohash值的Geohash值.

因此,例如,1600宾夕法尼亚大道,华盛顿特区解决:38.897,-77.036

使用geohash算法,此纬度和经度将转换为:dqcjqcp84c6e

可以通过将此geohash截断为:dqcjqc来描述此点周围的简单边界框

但是,'dqcjqcp84c6e'不在'dqcjqc'中居中,并且在'dqcjqc'内搜索可能会错过一些所需的目标.

因此,我们可以使用Geohash的数学属性来快速计算'dqcjqc'的邻居; 我们发现它们是:'dqcjqf','dqcjqb','dqcjr1','dqcjq9','dqcjqd','dqcjr4','dqcjr0','dqcjq8'

这为我们提供了一个围绕'dqcjqcp84c6e'大约2km x 1.5km的边界框,允许仅对9个键进行数据库搜索:SELECT*FROM table WHERE LEFT(geohash,6)IN('dqcjqc','dqcjqf','dqcjqb' , 'dqcjr1', 'dqcjq9', 'dqcjqd', 'dqcjr4', 'dqcjr0', 'dqcjq8');

转换为SimpleDB查询,where GeoHash6 in('dqcjqc', 'dqcjqf', 'dqcjqb', 'dqcjr1', 'dqcjq9', 'dqcjqd', 'dqcjr4', 'dqcjr0', 'dqcjq8')然后您将对结果进行Haversine过滤,以便仅获取搜索范围内的项目.