View a markdown version of this page

通过 Amazon DocumentDB 查询地理空间数据 - Amazon DocumentDB

本文属于机器翻译版本。若本译文内容与英语原文存在差异,则一律以英文原文为准。

通过 Amazon DocumentDB 查询地理空间数据

本节将介绍可以怎样使用 Amazon DocumentDB 来查询地理空间数据。阅读本节后,您将能够回答如何在 Amazon DocumentDB 中存储、查询和索引化地理空间数据。

概述

地理空间的常见用例涉及来自数据的邻近分析。例如,“查找距离西雅图 50 英里范围内的所有机场”,或“查找距离给定位置最近的餐厅”。Amazon DocumentDB 使用 GeoJSON 规范来表示地理空间数据。GeoJSON 是坐标空间中形状 JSON-formatting 的开源规范。GeoJSON 坐标捕获经度和纬度,表示在类地球球体上的位置。

索引化和存储地理空间数据

Amazon DocumentDB 使用“点” GeoJSON 类型来存储地理空间数据。每个 GeoJSON 文档(或子文档)通常由两个字段组成:

  • 类型:要被表示的形状,它告知 Amazon DocumentDB 如何解释“坐标”字段。目前,Amazon DocumentDB 仅支持点

  • 坐标:表示为数组中对象的经纬度对:[经度、纬度]

Amazon DocumentDB 还使用 2dsphere 索引来索引化地理空间数据。Amazon DocumentDB 支持索引化点。Amazon DocumentDB 支持用 2dsphere 索引化进行邻近查询。

让我们考虑一个场景,即您正在为送餐服务构建一个应用程序。您希望要在 Amazon DocumentDB 中存储各种餐厅的经纬度对。为此,我们首先建议您对地理空间字段创建一个包含经纬度对的索引。

use restaurantsdb db.usarestaurants.createIndex({location:"2dsphere"})

该命令的输出内容类似如下所示:

{ "createdCollectionAutomatically" : true, "numIndexesBefore" : 1, "numIndexesAfter" : 2, "ok" : 1 }

创建索引后,您可以开始将数据插入 Amazon DocumentDB 集合。

db.usarestaurants.insert({ "state":"Washington", "city":"Seattle", "name":"Thai Palace", "rating": 4.8, "location":{ "type":"Point", "coordinates":[ -122.3264, 47.6009 ] } }); db.usarestaurants.insert({ "state":"Washington", "city":"Seattle", "name":"Noodle House", "rating": 4.8, "location":{ "type":"Point", "coordinates":[ -122.3517, 47.6159 ] } }); db.usarestaurants.insert({ "state":"Washington", "city":"Seattle", "name":"Curry House", "rating": 4.8, "location":{ "type":"Point", "coordinates":[ -121.4517, 47.6229 ] } });

查询地理空间数据

Amazon DocumentDB 支持对地理空间数据的邻近查询、包含查询和交叉点查询。一个良好的邻近查询示例是查找距另一个点(城市)小于某个距离且大于某个距离的所有点(所有机场)。包含查询的一个很好的例子是查找位于指定(纽约州)的所有点 area/polygon (所有机场)。一个良好的交叉点查询示例是查找与某个点(城市)相交的多边形(州)。您可以使用以下地理空间运算符从数据中获取见解。

  • $nearSphere$nearSphere 是一个查找运算符,支持查找距 GeoJSON 点最近处到最远处的点。

  • $geoNear$geoNear 是一个聚合运算符,支持计算以米为单位的距 GeoJSON 点的距离。

  • $minDistance$minDistance 是一个查找运算符,结合 $nearSphere$geoNear 一起用于筛选距中心点至少指定最小距离的文档。

  • $maxDistance$maxDistance 是一个查找运算符,结合 $nearSphere$geoNear 一起用于筛选距中心点至多指定最大距离的文档。

  • $geoWithin$geoWithin 是一个查找运算符,支持查找包含具有以下地理空间数据的文档,这些数据完全存在于指定形状(如多边形)范围内。

  • $geoIntersects$geoIntersects 是一个查找运算符,支持查找其地理空间数据与指定 GeoJSON 对象相交的文档。

注意

$geoNear$nearSphere 要求您在邻近查询中使用的 GeoJSON 字段上有 2dsphere 索引。

示例 1

在此示例中,您将学习如何查找按照距某地址(点)最近距离排序的所有餐厅(点)。

要执行这样的查询,您可以使用 $geoNear 计算一组点距另一点的距离。您也可以添加 distanceMultiplier 来测量以千米计的距离。

db.usarestaurants.aggregate([ { "$geoNear":{ "near":{ "type":"Point", "coordinates":[ -122.3516, 47.6156 ] }, "spherical":true, "distanceField":"DistanceKilometers", "distanceMultiplier":0.001 } } ])

上述命令将返回按照距指定点的距离(最近到最远)排序的餐厅。该命令的输出内容类似如下所示

{ "_id" : ObjectId("611f3da985009a81ad38e74b"), "state" : "Washington", "city" : "Seattle", "name" : "Noodle House", "rating" : 4.8, "location" : { "type" : "Point", "coordinates" : [ -122.3517, 47.6159 ] }, "DistanceKilometers" : 0.03422834547294996 } { "_id" : ObjectId("611f3da185009a81ad38e74a"), "state" : "Washington", "city" : "Seattle", "name" : "Thai Palace", "rating" : 4.8, "location" : { "type" : "Point", "coordinates" : [ -122.3264, 47.6009 ] }, "DistanceKilometers" : 2.5009390081704277 } { "_id" : ObjectId("611f3dae85009a81ad38e74c"), "state" : "Washington", "city" : "Seattle", "name" : "Curry House", "rating" : 4.8, "location" : { "type" : "Point", "coordinates" : [ -121.4517, 47.6229 ] }, "DistanceKilometers" : 67.52845344856914 }
注意

在 Amazon DocumentDB 8.0(引擎补丁版本 4.0.5748)limit及更高版本中,该$geoNear阶段的和num选项以及 100 个文档的默认限制已被弃用。以下示例仅使用limitnum适用于亚马逊 DocumentDB 8.0(引擎补丁版本 4.0.4448)和更早版本。

要限制查询中的结果数量,可使用 limitnum 选项。

limit:

db.usarestaurants.aggregate([ { "$geoNear":{ "near":{ "type":"Point", "coordinates":[ -122.3516, 47.6156 ] }, "spherical":true, "distanceField":"DistanceKilometers", "distanceMultiplier":0.001, "limit": 10 } } ])

num:

db.usarestaurants.aggregate([ { "$geoNear":{ "near":{ "type":"Point", "coordinates":[ -122.3516, 47.6156 ] }, "spherical":true, "distanceField":"DistanceKilometers", "distanceMultiplier":0.001, "num": 10 } } ])

示例 2

在此示例中,您将学习如何查找距特定地址(点)2 千米范围内的所有餐厅(点)。要执行此类查询,您可以在距 GeoJSON 点的最小值 $minDistance 和最大值 $maxDistance 范围内使用 $nearSphere

db.usarestaurants.find({ "location":{ "$nearSphere":{ "$geometry":{ "type":"Point", "coordinates":[ -122.3516, 47.6156 ] }, "$minDistance":1, "$maxDistance":2000 } } }, { "name":1 })

上面的命令将返回距指定点最大距离 2 千米的餐厅。该命令的输出内容类似如下所示

{ "_id" : ObjectId("611f3da985009a81ad38e74b"), "name" : "Noodle House" }

限制

Amazon DocumentDB 不支持对多边形、、、 LineString MultiPoint MultiPolygon、 MultiLineString和进行查询或索引。 GeometryCollection