Microsoft SQL Server 上的地理数据

Posted

技术标签:

【中文标题】Microsoft SQL Server 上的地理数据【英文标题】:Geographic data on Microsoft SQL Server 【发布时间】:2015-09-06 10:08:36 【问题描述】:

我有一个 SQL Server 表,其地理点类型为 [latitude, longitude]。目前,我只有很少的分数,但是,随着时间的推移,我希望我的表格会显着增长。

稍后,我将需要通过接近另一个点来查询我的表。有没有任何标准化的方法可以有效地做到这一点?例如某种地理空间索引?您的最佳做法是什么?

我需要的查询在伪代码中将如下所示:

-- lat0, lng0 and radius0 are search parameters
-- distance() is function which computes distance between two points
SELECT id, lat, lng 
FROM myTable 
WHERE distance(lat, lng, lat0, lng0) < radius0

【问题讨论】:

如果您使用的是 SQL Server 2008 或更新版本 - 是的,有特定的地理空间数据类型 GEOMETRYGEOGRAPHY 以及可用于处理此问题的支持函数 - 请参阅Types of Spatial Data 介绍 【参考方案1】:

要添加到 alroc 的答案,您也可以创建一个带有索引的计算持久列。

ALTER TABLE my_table ADD geo AS GEOGRAPHY::Point (
        latitude
        ,longitude
        ,4326
        ) persisted;
CREATE spatial INDEX SI_my_table__geo ON my_table (geo);

SELECT TOP 5 @point.STDistance(geo) as distance_meters 
    ,id
    ,location_name
    ,latitude
    ,longitude
FROM my_table;

【讨论】:

【参考方案2】:

正如 marc_s 所提到的,SQL Server 2008+ 具有您可以使用的地理空间类型。如果您想在myTable 上保持纬度和经度分开,但也有一个表示这些坐标的地理空间列,您可以使用计算列(但请注意可能导致的性能问题),这样您就没有重复的数据放在桌子上。

[latlong] AS ([geography]::Point([Latitude],[Longitude],(4326)))

然后,要查找另一个点半径内的任何点,您可以使用geography 类型的STDistance 方法。

declare @radius int = 100000;
declare @p1 geography = geography::STGeomFromText('POINT(-122.33365 47.612033)',4326);
select * from myTable where @p1.STDistance(latlong) <= @radius;

请注意,距离以米为单位。

【讨论】:

谢谢,这就是我正在寻找的。索引怎么样,GEOGRAPHY 列是否支持? 是的,您可以创建空间索引,但还有一些额外的要求。我认为您的 PK 必须是聚集索引(不能是非聚集索引)。

以上是关于Microsoft SQL Server 上的地理数据的主要内容,如果未能解决你的问题,请参考以下文章

SQL Server 在地理列上返回错误

SQL Server 2008 在具有空间索引的可空地理列上的性能

几何列上的 SQL Server 平面世界地图

Microsoft Visual Studio 2012 上的地理地图

Microsoft][ODBC SQL Server Driver][DBNETLIB]SQL Server不存在或访问被拒绝

Microsoft Azure 网站上的地理服务器