通过腾讯位置服务获取的城市轮廓判断一个经纬度是否在城市轮廓内

1、返回的城市轮廓数据参考
在这里插入图片描述
工具方法

    /**
     * 判断点是否在多边形内,如果点位于多边形的顶点或边上,也算做点在多边形内,直接返回true
     *
     * @param point   检测点
     * @param polygon 多边形的顶点
     * @return 点在多边形内返回true, 否则返回false
     */
    public static boolean isPtInPoly(Point2D.Double point, List<Point2D.Double> polygon) {
        assertParams(point, polygon);

        int N = polygon.size();
        //如果点位于多边形的顶点或边上,也算做点在多边形内,直接返回true
        boolean boundOrVertex = true;
        //cross points count of x
        int intersectCount = 0;
        //浮点类型计算时候与0比较时候的容差
        double precision = 2e-10;
        //neighbour bound vertices
        Point2D.Double p1, p2;
        //当前点
        Point2D.Double p = point;

        //left vertex
        p1 = polygon.get(0);
        //check all rays
        for (int i = 1; i <= N; ++i) {
            if (p.equals(p1)) {
                //p is an vertex
                return boundOrVertex;
            }

            //right vertex
            p2 = polygon.get(i % N);
            //ray is outside of our interests
            if (p.x < Math.min(p1.x, p2.x) || p.x > Math.max(p1.x, p2.x)) {
                p1 = p2;
                //next ray left point
                continue;
            }

            //ray is crossing over by the algorithm (common part of)
            if (p.x > Math.min(p1.x, p2.x) && p.x < Math.max(p1.x, p2.x)) {
                //x is before of ray
                if (p.y <= Math.max(p1.y, p2.y)) {
                    //overlies on a horizontal ray
                    if (p1.x == p2.x && p.y >= Math.min(p1.y, p2.y)) {
                        return boundOrVertex;
                    }

                    //ray is vertical
                    if (p1.y == p2.y) {
                        //overlies on a vertical ray
                        if (p1.y == p.y) {
                            return boundOrVertex;
                            //before ray
                        } else {
                            ++intersectCount;
                        }
                        //cross point on the left side
                    } else {
                        //cross point of y
                        double xinters = (p.x - p1.x) * (p2.y - p1.y) / (p2.x - p1.x) + p1.y;
                        //overlies on a ray
                        if (Math.abs(p.y - xinters) < precision) {
                            return boundOrVertex;
                        }

                        //before ray
                        if (p.y < xinters) {
                            ++intersectCount;
                        }
                    }
                }
                //special case when ray is crossing through the vertex
            } else {
                //p crossing over p2
                if (p.x == p2.x && p.y <= p2.y) {
                    //next vertex
                    Point2D.Double p3 = polygon.get((i + 1) % N);
                    //p.x lies between p1.x & p3.x
                    if (p.x >= Math.min(p1.x, p3.x) && p.x <= Math.max(p1.x, p3.x)) {
                        ++intersectCount;
                    } else {
                        intersectCount += 2;
                    }
                }
            }
            //next ray left point
            p1 = p2;
        }

        //偶数在多边形外
        if (intersectCount % 2 == 0) {
            return false;
            //奇数在多边形内
        } else {
            return true;
        }
    }

	//格式化数据
    public static List<Point2D.Double> addLocationList(JSONArray array){
        List<Point2D.Double> points = new ArrayList<>();
        int size = array.size() / 2;
        for (int i = 0; i < size; i++) {
            Point2D.Double e = new Point2D.Double(array.getDouble(i*2), array.getDouble(i*2+1));
            points.add(e);
        }
        return points;
    }

调用方法:

			//JSON.parseArray(city.getCitypolygon())为腾讯接口返回的数据,
           List<Point2D.Double> points = locationUtil.addLocationList(JSON.parseArray(city.getCitypolygon()));// 格式化数据
           // 用户位置 经度和纬度
           Point2D.Double userLocation = new Point2D.Double(Convert.toDouble(stringList.get(1)), Convert.toDouble(stringList.get(2)));
            if (!locationUtil.isPtInPoly(userLocation, points)) {
            // 不在城市轮廓范围内
           }
           // 在城市轮廓范围内
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值