js 如何判断一个指定的位置点坐标是否落在一个多边形区域内?

1 场景

  业务场景举例:快递选择收获区域、车辆电子围栏、运动轨迹路线、地理位置信息检测范围和地图等过滤等等。
  比方说地图上有一块区域(抽象成多边形),然后里面每一个位置点(像素点)都有对应的GPS的经纬度坐标值,题目要求的就是判断任意点(用户输入的信息)与多边形的位置关系(是否在里面还是在图形区域外面)。

1.1 方案

  设:需要判断的目标点为P
  参数
  aLat: P的纬度
  aLon: P的经度
  pointList: 单个多边形区域顶点数组。如果有多个独立区域,则分别调用本方法,只要有一次为ture即表示在区域内。
在这里插入图片描述

1.2 理论支持

  目前比较通用的就是射线法和坐标轴法,而我采用的就是X轴射线法。
  判断一个点向左的射线跟一个多边形的交叉点有几个,如果结果为奇数的话那么说明这个点落在多边形中,反之则不在。
  如果从需要判断的点出发的一条射线与该多边形的焦点个数为奇数,则该点在此多边形内,否则该点在此多边形外。(射线不能与多边形顶点相交)

1.3 编程思路

  该程序的思路是从A点出发向左做一条水平射线(平行于x轴,向X轴的反方向),判断与各边是否有焦点。
dLon1, dLon2, dLat1, dLat2分别表示边的起点和终点的经度和纬度(x轴和y轴)。
  先判断A点是否在边的两端点d1和d2的水平平行线之间,不在则不可能有交点,继续判断下一条边。
在之间则说明可能与A点向左的射线有交点,接下来利用几何方法得到A点的水平直线与该边交点的x坐标。
然后判断交点的x坐标在A点的左侧还是右侧,左侧则总交点数加一,右侧则不在A点左射线上,继续判断下一条边。
  代码讲解: 主要的类有两个↓↓
一个是坐标点的抽象类(点的坐标位置),另一个是位置关系判断工具类(判断点和多边形的关系)。
  因为坐标描点要涉及到坐标以及小数点的经纬关系,故要用到浮点型运算,也就是要使用到double双精度。而地图涉及到很多个像素点构成的图形区域,故要用到list数组。结果要展示需要用到js代码
utilofMap.js文件:

function IsPtInPoly(aLat, aLon, pointList) {
  /* 
  :param aLon: double 经度 
  :param aLat: double 纬度 
  :param pointList: list [{latitude: 22.22, longitude: 113.113}...] 多边形点的顺序需根据顺时针或逆时针,不能乱 
  */
  var iSum = 0  
  var iCount = pointList.length
    
  if(iCount < 3) {
      return false 
  }
  //  待判断的点(x, y) 为已知值
  var y = aLat
  var x = aLon
  for(var i = 0; i < iCount; i++) {
      var y1 = pointList[i].latitude  
      var x1 = pointList[i].longitude
      if(i == iCount - 1) {
          var y2 = pointList[0].latitude
          var x2 = pointList[0].longitude
      } else {
          var y2 = pointList[i + 1].latitude  
          var x2 = pointList[i + 1].longitude
      }
      // 当前边的 2 个端点分别为 已知值(x1, y1), (x2, y2)
      if (((y >= y1) && (y < y2)) || ((y >= y2) && (y < y1))) {
          //  y 界于 y1 和 y2 之间
          //  假设过待判断点(x, y)的水平直线和当前边的交点为(x_intersect, y_intersect),有y_intersect = y
          // 则有(2个相似三角形,公用顶角,宽/宽 = 高/高):|x1 - x2| / |x1 - x_intersect| = |y1 - y2| / |y1 - y|
          if (Math.abs(y1 - y2) > 0) {
              var x_intersect = x1 - ((x1 - x2) * (y1 - y)) / (y1 - y2);  
              if(x_intersect < x) {
                  iSum += 1 
              }
          }
      } 
  }
  if(iSum % 2 != 0) {
      return true  
  }else {
      return false 
  }  
}
module.exports = {
  IsPtInPoly: IsPtInPoly,
};
  • 2
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
要在Redis中判断一个是否坐标区域内,可以使用Redis的地理空间数据类型和相关命令。Redis支持存储和查询地理空间数据,使其成为一个强大的地理信息系统。 首先,你需要使用Redis的地理空间数据类型,例如有序集合(Sorted Set),来存储多边形区域坐标。你可以将每个坐标作为一个成员,将其经度作为score。通过有序集合的score,可以快速对坐标进行排序和范围查询。 接下来,你可以使用Redis的地理空间命令,如GEORADIUS,来判断一个是否多边形区域内。GEORADIUS命令可以根据指定的经度、纬度和半径,返回在指定范围内的坐标。将要判断作为参数传递给GEORADIUS命令,并设置一个适当的半径,如果返回的结果中包含了这个,那么就说明这个多边形区域内。 需要注意的是,Redis的地理空间命令默认使用的是WGS84坐标系,即经度和纬度使用的是度数。因此,在使用这些命令时,需要将的经度和纬度转换为度数,并确保它们与多边形区域中的坐标使用相同的坐标系。 总结来说,为了在Redis中判断一个是否坐标区域内,你可以使用Redis的地理空间数据类型和地理空间命令。将多边形区域坐标存储为有序集合,并使用GEORADIUS命令来查询指定范围内的坐标,以判断一个是否多边形区域内。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值