查询最近的邻居的空间数据

适用于: SQL Server Azure SQL 数据库 Azure SQL 托管实例 Microsoft Fabric 中的 SQL 分析终结点 Microsoft Fabric 中的仓库

与空间数据一起使用的常见查询是最近的邻居查询。 最近的邻居查询用于查找与特定空间对象最近的空间对象。 例如,网站的商店定位符通常必须找到离客户位置最近的商店位置。

最近的邻居查询可以采用各种有效的查询格式编写,但对于最接近的邻居查询,必须使用以下语法。

语法

SELECT TOP ( number )  
        [ WITH TIES ]  
        [ * | expression ]   
        [, ...]  
    FROM spatial_table_reference, ...   
        [ WITH   
            (   
                [ INDEX ( index_ref ) ]   
                [ , SPATIAL_WINDOW_MAX_CELLS = <value>]   
                [ ,... ]   
            )   
        ]  
    WHERE   
        column_ref.STDistance ( @spatial_ object )   
            {   
                [ IS NOT NULL ] | [ < const ] | [ > const ]   
                | [ <= const ] | [ >= const ] | [ <> const ] ]   
            }  
            [ AND { other_predicate } ]   
    }  
    ORDER BY column_ref.STDistance ( @spatial_ object ) [ ,...n ]  
[ ; ]  

最近的邻居查询和空间索引

在 SQL Server 中, TOPORDER BY 句用于对空间数据列执行最近的邻居查询。 对于空间列数据类型,ORDER BY 子句包含对 STDistance() 方法的调用。 TOP 子句指示针对该查询要返回的对象数。

若要使用空间索引,必须满足最接近的邻居查询的以下要求:

  1. 空间索引必须存在于其中一个空间列上,并且 STDistance() 方法必须在 WHEREORDER BY 子句中使用该空间列。

  2. TOP 子句不能包含 PERCENT 语句。

  3. WHERE 子句必须包含 STDistance() 方法。

  4. 如果 WHERE 子句中有多个谓词,则必须使用 AND 连词将包含 STDistance() 方法的谓词连接到其他谓词。 STDistance() 方法不能是 WHERE 子句的可选部分。

  5. ORDER BY 子句中的第一个表达式必须使用 STDistance() 方法。

  6. ORDER BY 子句中第一个 STDistance() 表达式的排序顺序必须是 ASC

  7. 必须筛选掉 STDistance 返回 NULL 的所有行。

警告

如果将地理几何图形数据类型作为参数的方法,则对于这些类型而言,如果 SRID 不同,则返回NULL这些方法。

建议将新的空间索引分割用于最接近的邻居查询中使用的索引。 有关空间索引分割的详细信息,请参阅 空间数据

示例 1

下面的代码示例演示了可以使用空间索引的最接近的邻居查询。 本示例使用 Person.Address 示例数据库中的 AdventureWorks2022 表。

USE AdventureWorks2022  
GO  
DECLARE @g geography = 'POINT(-121.626 47.8315)';  
SELECT TOP(7) SpatialLocation.ToString(), City FROM Person.Address
WHERE SpatialLocation.STDistance(@g) IS NOT NULL  
ORDER BY SpatialLocation.STDistance(@g);  

在 SpatialLocation 列上创建空间索引,以查看最近的邻居查询如何使用空间索引。 有关创建空间索引的详细信息,请参阅 Create, Modify, and Drop Spatial Indexes

示例 2

下面的代码示例演示了无法使用空间索引的最接近的邻居查询。

USE AdventureWorks2022  
GO  
DECLARE @g geography = 'POINT(-121.626 47.8315)';  
SELECT TOP(7) SpatialLocation.ToString(), City FROM Person.Address  
ORDER BY SpatialLocation.STDistance(@g);  

该查询缺少在语法部分中指定的窗体中使用 STDistance()WHERE 子句,因此它无法使用空间索引。