SQL 查询地理信息中指定距离范围内的记录

来源:互联网 发布:天庭淘宝店无常 编辑:程序博客网 时间:2024/05/21 17:05

目标:选取在指定位置1公里范围的记录
测试数据:指定时间范围内,16万记录
跟据测试结果,如果不是需要很高精度,用第一种方法就可以了

方法1:按矩形算
优点:快,缺点:不是圆型的范围,平均执行150ms

DECLARE @GGP_LOCATE_POINT GEOGRAPHY = GEOGRAPHY::Point( 22.26663,113.821256666667, 4326);  DECLARE @FLT_LONGITUDE   FLOAT,  @FLT_LATITUDE   FLOAT  --纬度SELECT @FLT_LONGITUDE =113.821256666667, @FLT_LATITUDE =22.26663SELECT @GGP_LOCATE_POINT.STDistance(GEOGRAPHY::Point([LATITUDE],[LONGITUDE], 4326)) as [验证距离], *  FROM [目标表]WHERE [ALERT_TIME] BETWEEN '2015-09-08' AND  '2015-09-28'AND [LATITUDE]  BETWEEN @FLT_LATITUDE-0.010 AND @FLT_LATITUDE+0.010AND [LONGITUDE] BETWEEN @FLT_LONGITUDE-0.010 AND @FLT_LONGITUDE+0.010

方法2:计算每个坐标的距离(圆),平均执行5500ms

DECLARE @GGP_LOCATE_POINT GEOGRAPHY = GEOGRAPHY::Point( 22.26663,113.821256666667, 4326);  SELECT *  FROM [dbo].[ALERT]WHERE [ALERT_TIME] BETWEEN '2015-09-08' AND  '2015-09-28'AND  @GGP_LOCATE_POINT.STDistance(GEOGRAPHY::Point([LATITUDE],[LONGITUDE], 4326))<=1000

方法3:计算目标是否在范围内,平均执行7500ms

DECLARE @GGP_LOCATE_POINT GEOGRAPHY = GEOGRAPHY::Point( 22.26663,113.821256666667, 4326);  DECLARE @buffer GEOGRAPHY;set @buffer=@GGP_LOCATE_POINT.STBuffer(1000);SELECT *  FROM [dbo].[ALERT]WHERE [ALERT_TIME] BETWEEN '2015-09-08' AND  '2015-09-28'AND @buffer.Filter(GEOGRAPHY::Point([LATITUDE],[LONGITUDE], 4326))>1000

补充:计算指定范围对应的经纬度大小

//地球子午线(南极到北极的连线)长度39940.67公里,纬度一度合110.94公里,一分合1.849公里,一秒合30.8米,不同纬度的间距是一样的。//地球赤道圈长度40075.36公里,深圳在北纬22度左右,纬度圈长为111.32*cos(a),//因此这里的经度一度合103.566436555110152670083196192/// <summary>/// 获取指定距离的经度/// </summary>/// <param name="org">对应的纬度</param>/// <param name="range"></param>/// <returns></returns>public double GetLongitude(double org, float range){    // 1 经度的距离为 111.32*cos(a)    const double n = 1113200f;    double angle = Math.PI * org / 180.0;    return range / (n * Math.Cos(angle));}/// <summary>/// 获取指定距离的纬度/// </summary>/// <param name="org"></param>/// <param name="range"></param>/// <returns></returns>public double GetLatitude( float range){    // 1 纬度的距离为 110.94公里    const double n = 1109400f;    return range / n;}
0 0
原创粉丝点击