地理信息搜索(GEO SEARCH)

可以使用Crate的geo_point和geo_shape数据类型来存储和查询很多种类的地理信息。利用这些支持可以用来存储地理位置,道路,形状,区域和其他实体信息。这些信息可以用来查询距离,容量,马路口等,使有可能创建具有丰富地理特性的app和服务。

地理形状使用指定索引存储。地理位置点用它们的坐标来表示。它们表示为相应数据类型的列。

在geo_shape列上使用地理位置索引,以便加速对地理位置甚至复杂形状的搜索。这个索引过程会导致不准确的呈现(查看geo_shape获取更多详情)。Crate不能操作形状矢量,仅仅是一种具有给定精度的格子。

创建包含地理信息的表很简单:

cr> CREATE TABLE country (
...   name string,
...   country_code string primary key,
...   shape geo_shape INDEX USING 'geohash' WITH (precision='100m'),
...   capital string,
...   capital_location geo_point
... ) WITH (number_of_replicas=0);
CREATE OK (... sec)

这个表将包含一个国家的形状和它的首都的位置以及其他元数据。使用最大精度为100米的geohash索引来索引化位置信息(更多信息,查看Geo形状索引数据结构)。

插入Austria:

cr> INSERT INTO country (mame, country_code, shape, capital, capital_location)
... VALUES (
...  'Austria',
...  'at',
...  {type='Polygon', coordinates=[[
...        [16.979667, 48.123497], [16.903754, 47.714866],
...        [16.340584, 47.712902], [16.534268, 47.496171],
...        [16.202298, 46.852386], [16.011664, 46.683611],
...        [15.137092, 46.658703], [14.632472, 46.431817],
...        [13.806475, 46.509306], [12.376485, 46.767559],
...        [12.153088, 47.115393], [11.164828, 46.941579],
...        [11.048556, 46.751359], [10.442701, 46.893546],
...        [9.932448,  46.920728], [9.47997,   47.10281 ],
...        [9.632932,  47.347601], [9.594226,  47.525058],
...        [9.896068,  47.580197], [10.402084, 47.302488],
...        [10.544504, 47.566399], [11.426414, 47.523766],
...        [12.141357, 47.703083], [12.62076,  47.672388],
...        [12.932627, 47.467646], [13.025851, 47.637584],
...        [12.884103, 48.289146], [13.243357, 48.416115],
...        [13.595946, 48.877172], [14.338898, 48.555305],
...        [14.901447, 48.964402], [15.253416, 49.039074],
...        [16.029647, 48.733899], [16.499283, 48.785808],
...        [16.960288, 48.596982], [16.879983, 48.470013],
...        [16.979667, 48.123497]]
...  },
...  'Vienna',
...  [16.372778, 48.209206]
... );
INSERT OK, 1 row affected (... sec)

注意

地理形状必须使用ISO 19107来完全校验。如果你有导入geo数据的问题,他们可能没有完全校验。在大多数情况下,他们将被使用下面的工具来修复:https://github.com/tudelft3d/prepair

地理位置点可以作为一个带有lon和lat的double数组,如上所示或者作为WKT的字符串。

地理形状可以被当做GeoJSON对象或者参数插入,如上所示和WKT的字符串。

当涉及到对你的地理数据有一些有意义的洞察是,Crate支持不同类型的地理查询。

快速查询和利用地理索引的方式是使用Match谓词:

Match Predicate

MATCH谓词可以用来在索引或者索引列上执行多种查询。同时他也可用来执行全文搜索在string类型的分析索引上,有人可以在地理索引上操作,查询地理新装和点的关系。

MATCH (column_ident, query_term) [ using match_type ]

地理搜索的匹配谓词支持将geo_shape索引列的单个column_ident作为第一个参数。

第二个参数,query_term被用来在索引geo_shape之间匹配。

匹配操作有匹配类型match_type决定,match_type将决定我们想要匹配的空间关系。可用的match_type有:

match_type 详情
(相交)intersects: (默认)如果两个形状共享一些点和或者区域,它们是相交的。并且认为会用此匹配类型。这也排除了遏制或完全平等
(不相交)disjoint: 如果两个形状没有共享的点或者区域,则他们是不相交的。这是相交的反面。
(包含)within: 如果索引列column_ident 的形状完全在query_term形状里面,则认为它们使用此匹配类型

注意
匹配谓词只能在where子句中使用而且必须为用户创建的表。在MATCH谓词不支持对系统表的操作。

注意 一个谓词不能组合所有一个join关系的所有列。

注意 MATCH谓词不能用于连接的两个关系的列,如果它们不能在逻辑上分别应用于它们中的每一个。例如: 这个是允许的: FROM t1, t2 WHERE match(t1.shape, ‘POINT(1.1 2.2)’) AND match(t2.shape, ‘POINT(3.3 4.4)’); 但是这个不允许: FROM t1, t2 WHERE match(t1.shape, ‘POINT(1.1 2.2)’) OR match(t2.shape, ‘POINT(3.3 4.4)’);

cr> SELECT name from countries
... WHERE
...  match(
...   shape,
...   'LINESTRING (13.3813 52.5229, 11.1840 51.5497, 8.6132 50.0782, 8.3715 47.9457, 8.5034 47.3685)'
... );
+------+
| name |
+------+
+------+
SELECT 0 rows in set (... sec)
cr> SELECT name from countries
... WHERE
...  match(
...   shape,
...   'LINESTRING (13.3813 52.5229, 11.1840 51.5497, 8.6132 50.0782, 8.3715 47.9457, 8.5034 47.3685)'
...  ) USING disjoint;
+---------+
| name    |
+---------+
| Austria |
+---------+
SELECT 1 row in set (... sec)

精确查询(Exact Queries)

精确查询使用下面标准函数:

  • intersects(geo_shape, geo_shape) returns boolean
  • within(shape1, shape2) returns boolean
  • distance(geo_point1, geo_point2) returns double

他们是精确的,但是这会带来一些性能代价。他们不使用索引但能在GeoJSON上工作,插入计算的形状向量。这个访问代价相当高而且可能减您的查询。为了查询更快,使用Match谓词。

但在有限结果集上执行,他们将帮助您精确洞察您的地理数据:

cr> SELECT within(capital_location, shape) AS capital_in_country
... FROM countries ORDER BY country_code;
+--------------------+
| capital_in_country |
+--------------------+
| TRUE               |
+--------------------+
SELECT 1 row in set (... sec)
cr> SELECT distance(capital_location, [0, 0]) as from_northpole
... FROM countries ORDER BY country_code;
+--------------------+
| from_northpole     |
+--------------------+
| 1234.2345          |
+--------------------+
SELECT 1 row in set (... sec)
cr> SELECT intersects(
...   {type='LineString', coordinates=[[13.3813, 52.5229],
                                       [11.1840, 51.5497],
                                       [8.6132,  50.0782],
                                       [8.3715,  47.9457],
                                       [8.5034,  47.3685]]},
...   shape) as berlin_zurich_intersects
... FROM countries ORDER BY country_code;
+--------------------------+
| berlin_zurich_intersects |
+--------------------------+
| FALSE                    |
+--------------------------+
SELECT 1 row in set (... sec)

尽管如此,这些标准函数可以在允许使用标准函数的SQL查询中的任何地方使用。

results matching ""

    No results matching ""