查询优化问题(空间)
Query Optimization Problems (spatial)
我有两个包含空间数据的数据集。
数据集 1 大约有 15,000,000 条记录。
数据集 2 大约有 16,000,000 条记录。
两者都使用地理数据类型(GPS坐标),所有记录都是点。
两个表都有 cells_per_object = 1 的空间索引,级别是 (HIGH, HIGH, HIGH, HIGH)
所有点都位于一个全局范围内的小区域(1 U.S. 州)。这些点足够分散,可以保证使用地理而不是几何投影。
DECLARE @g GEOGRAPHY
SET @g = (SELECT TOP 1 GPSPoint FROM Dataset1)
EXEC sp_help_spatial_geography_index 'Dataset1', 'Dataset1_SpatialIndex', 0, @g
演出
propvalue-propname
1-Total_Number_Of_ObjectCells_In_Level0_For_QuerySample
28178-Total_Number_Of_ObjectCells_In_Level1_In_Index
1-Total_Number_Of_ObjectCells_In_Level4_For_QuerySample
14923330-Total_Number_Of_ObjectCells_In_Level4_In_Index
1-Total_Number_Of_Intersecting_ObjectCells_In_Level1_In_Index
1-Total_Number_Of_Intersecting_ObjectCells_In_Level4_For_QuerySample
14923330-Total_Number_Of_Intersecting_ObjectCells_In_Level4_In_Index
1-Total_Number_Of_Border_ObjectCells_In_Level0_For_QuerySample
28177-Total_Number_Of_Border_ObjectCells_In_Level1_In_Index
740-Number_Of_Rows_Selected_By_Primary_Filter
0-Number_Of_Rows_Selected_By_Internal_Filter
740-Number_Of_Times_Secondary_Filter_Is_Called
1-Number_Of_Rows_Output
99.99504-Percentage_Of_Rows_NotSelected_By_Primary_Filter
0-Percentage_Of_Primary_Filter_Rows_Selected_By_Internal_Filter
0-Internal_Filter_Efficiency
0.135135-Primary_Filter_Efficiency
表示查询
DECLARE @g GEOGRPAHY
SET @g = (SELECT TOP 1 GPSPoint FROM Dataset1)
SELECT TOP 1
*
FROM
Dataset2 D
WHERE
@g.Filter(D.GPSPoint.STBuffer(1)) = 1
几乎需要一个小时才能完成。
我也试过
WITH TABLE1 AS (
SELECT
A.RecordID,
B.RecordID,
RANK() OVER (PARTITION BY A.RecordID ORDER BY A.GPSPoint.STDistance(B.GPSPoint) ASC) AS 'Ranking'
FROM
Dataset1 A
INNER JOIN
Dataset2 B
ON
B.GPSPoint.Filter(A.GPSPoint.STBuffer(1)) = 1
AND A.GPSPoint.STDistance(B.GPSPoint) <= 50
)
SELECT
*
FROM
TABLE1
WHERE
Ranking = 1
最终速度快了大约 1,000 倍,但按照这个速度,我尝试做的事情将需要查询 运行 六个月才能完成。老实说,我现在不知道该怎么办。最终目标是对dataset1中的每条记录进行最近邻搜索,以找到dataset2中最近的点,但这样似乎不可能。
有没有人有任何想法可以提高这个过程的效率?
试试这个:它基于 MSDN.
上的建议
SELECT TOP(1)
A.RecordID,
B.RecordID,
A.GPSPoint.STDistance(B.GPSPoint) AS Distance
FROM
Dataset1 A
INNER JOIN
Dataset2 B
ON
A.GPSPoint.STDistance(B.GPSPoint) <= 50
AND B.GPSPoint IS NOT NULL
ORDER BY BY A.GPSPoint.STDistance(B.GPSPoint) ASC
注意我已经删除了这个,首先尝试上面的查询,然后添加这些谓词并查看它如何影响索引。
B.GPSPoint.Filter(A.GPSPoint.STBuffer(1)) = 1
AND
//or try B.GPSPoint.STIntersects(A.GPSPoint.STBuffer(1)) = 1
最近邻查询必须满足以下要求才能使用空间索引:
- 空间索引必须出现在其中一个空间列上,并且 STDistance() 方法必须在 WHERE 和 ORDER BY 子句中使用该列。
- TOP 子句不能包含 PERCENT 语句。
- WHERE 子句必须包含 STDistance() 方法
- 如果 WHERE 子句中有多个谓词,则包含 STDistance() 方法的谓词必须通过 AND 连词连接到其他谓词。 STDistance() 方法不能位于 WHERE 子句的可选部分。
- ORDER BY 子句中的第一个表达式必须使用 STDistance() 方法。
- ORDER BY 子句中第一个 STDistance() 表达式的排序顺序必须是 ASC。
- 必须过滤掉 STDistance returns NULL 的所有行。
我有两个包含空间数据的数据集。
数据集 1 大约有 15,000,000 条记录。 数据集 2 大约有 16,000,000 条记录。
两者都使用地理数据类型(GPS坐标),所有记录都是点。
两个表都有 cells_per_object = 1 的空间索引,级别是 (HIGH, HIGH, HIGH, HIGH)
所有点都位于一个全局范围内的小区域(1 U.S. 州)。这些点足够分散,可以保证使用地理而不是几何投影。
DECLARE @g GEOGRAPHY
SET @g = (SELECT TOP 1 GPSPoint FROM Dataset1)
EXEC sp_help_spatial_geography_index 'Dataset1', 'Dataset1_SpatialIndex', 0, @g
演出
propvalue-propname
1-Total_Number_Of_ObjectCells_In_Level0_For_QuerySample
28178-Total_Number_Of_ObjectCells_In_Level1_In_Index
1-Total_Number_Of_ObjectCells_In_Level4_For_QuerySample
14923330-Total_Number_Of_ObjectCells_In_Level4_In_Index
1-Total_Number_Of_Intersecting_ObjectCells_In_Level1_In_Index
1-Total_Number_Of_Intersecting_ObjectCells_In_Level4_For_QuerySample
14923330-Total_Number_Of_Intersecting_ObjectCells_In_Level4_In_Index
1-Total_Number_Of_Border_ObjectCells_In_Level0_For_QuerySample
28177-Total_Number_Of_Border_ObjectCells_In_Level1_In_Index
740-Number_Of_Rows_Selected_By_Primary_Filter
0-Number_Of_Rows_Selected_By_Internal_Filter
740-Number_Of_Times_Secondary_Filter_Is_Called
1-Number_Of_Rows_Output
99.99504-Percentage_Of_Rows_NotSelected_By_Primary_Filter
0-Percentage_Of_Primary_Filter_Rows_Selected_By_Internal_Filter
0-Internal_Filter_Efficiency
0.135135-Primary_Filter_Efficiency
表示查询
DECLARE @g GEOGRPAHY
SET @g = (SELECT TOP 1 GPSPoint FROM Dataset1)
SELECT TOP 1
*
FROM
Dataset2 D
WHERE
@g.Filter(D.GPSPoint.STBuffer(1)) = 1
几乎需要一个小时才能完成。
我也试过
WITH TABLE1 AS (
SELECT
A.RecordID,
B.RecordID,
RANK() OVER (PARTITION BY A.RecordID ORDER BY A.GPSPoint.STDistance(B.GPSPoint) ASC) AS 'Ranking'
FROM
Dataset1 A
INNER JOIN
Dataset2 B
ON
B.GPSPoint.Filter(A.GPSPoint.STBuffer(1)) = 1
AND A.GPSPoint.STDistance(B.GPSPoint) <= 50
)
SELECT
*
FROM
TABLE1
WHERE
Ranking = 1
最终速度快了大约 1,000 倍,但按照这个速度,我尝试做的事情将需要查询 运行 六个月才能完成。老实说,我现在不知道该怎么办。最终目标是对dataset1中的每条记录进行最近邻搜索,以找到dataset2中最近的点,但这样似乎不可能。
有没有人有任何想法可以提高这个过程的效率?
试试这个:它基于 MSDN.
上的建议 SELECT TOP(1)
A.RecordID,
B.RecordID,
A.GPSPoint.STDistance(B.GPSPoint) AS Distance
FROM
Dataset1 A
INNER JOIN
Dataset2 B
ON
A.GPSPoint.STDistance(B.GPSPoint) <= 50
AND B.GPSPoint IS NOT NULL
ORDER BY BY A.GPSPoint.STDistance(B.GPSPoint) ASC
注意我已经删除了这个,首先尝试上面的查询,然后添加这些谓词并查看它如何影响索引。
B.GPSPoint.Filter(A.GPSPoint.STBuffer(1)) = 1
AND
//or try B.GPSPoint.STIntersects(A.GPSPoint.STBuffer(1)) = 1
最近邻查询必须满足以下要求才能使用空间索引:
- 空间索引必须出现在其中一个空间列上,并且 STDistance() 方法必须在 WHERE 和 ORDER BY 子句中使用该列。
- TOP 子句不能包含 PERCENT 语句。
- WHERE 子句必须包含 STDistance() 方法
- 如果 WHERE 子句中有多个谓词,则包含 STDistance() 方法的谓词必须通过 AND 连词连接到其他谓词。 STDistance() 方法不能位于 WHERE 子句的可选部分。
- ORDER BY 子句中的第一个表达式必须使用 STDistance() 方法。
- ORDER BY 子句中第一个 STDistance() 表达式的排序顺序必须是 ASC。
- 必须过滤掉 STDistance returns NULL 的所有行。