判断点是否在多边形内部---实测

判断点是否在多边形内部

注:
从网上看了好些个,思路了解了下,然后粘代码测试,发现很多都是错的,而且错的都一样,这里粘贴一个测试过的。主要差别在于应该先判断线段是否在左边,否则就会出现边界问题,计算错误。

# 判断点和线的位置关系
def isRayIntersectsSegment(poi,s_poi,e_poi): #[x,y] [lng,lat]
    # print(poi,s_poi,e_poi)
    #输入:判断点,边起点,边终点,都是[lng,lat]格式数组
    if s_poi[0]<poi[0] and e_poi[0]<poi[0]: #线段在射线左边
        return False
    
    if s_poi[1]==e_poi[1]: #排除与射线平行、重合,线段首尾端点重合的情况
        return False
    if s_poi[1]>poi[1] and e_poi[1]>poi[1]: #线段在射线上边
        return False
    if s_poi[1]<poi[1] and e_poi[1]<poi[1]: #线段在射线下边
        return False
    if s_poi[1]==poi[1] and e_poi[1]>poi[1]: #交点为下端点,对应spoint
        return False
    if e_poi[1]==poi[1] and s_poi[1]>poi[1]: #交点为下端点,对应epoint
        return False
    

    xseg=e_poi[0]-(e_poi[0]-s_poi[0])*(e_poi[1]-poi[1])/(e_poi[1]-s_poi[1]) #求交
    if xseg<poi[0]: #交点在射线起点的左侧
        return False
    return True  #排除上述情况之后

# 判断是否在多边形里面
def is_in_polygon(p,polygon):
    #polygon.append(polygon[0])
    # 注意,需要传入的列表中,首尾需要相连,即最后一个点是需要和第一个点相同的。
    # 构建多边形时需要注意不能有交叉存在
    x_num = 0
    for i in range(len(polygon)-1):
        if isRayIntersectsSegment(p,polygon[i],polygon[i+1]):
            x_num += 1
    return x_num % 2 == 1

这里也给出后端服务代码,使用python-flask搭建

from flask_cors import CORS
import json

import flask
from flask import request

cfg = None

app = flask.Flask(__name__)
CORS(app,supports_credentials=True)




# 判断点和线的位置关系
def isRayIntersectsSegment(poi,s_poi,e_poi): #[x,y] [lng,lat]
    # print(poi,s_poi,e_poi)
    #输入:判断点,边起点,边终点,都是[lng,lat]格式数组
    if s_poi[0]<poi[0] and e_poi[0]<poi[0]: #线段在射线左边
        return False
    
    if s_poi[1]==e_poi[1]: #排除与射线平行、重合,线段首尾端点重合的情况
        return False
    if s_poi[1]>poi[1] and e_poi[1]>poi[1]: #线段在射线上边
        return False
    if s_poi[1]<poi[1] and e_poi[1]<poi[1]: #线段在射线下边
        return False
    if s_poi[1]==poi[1] and e_poi[1]>poi[1]: #交点为下端点,对应spoint
        return False
    if e_poi[1]==poi[1] and s_poi[1]>poi[1]: #交点为下端点,对应epoint
        return False
    
    xseg=e_poi[0]-(e_poi[0]-s_poi[0])*(e_poi[1]-poi[1])/(e_poi[1]-s_poi[1]) #求交
    if xseg<poi[0]: #交点在射线起点的左侧
        return False
    return True  #排除上述情况之后

# 判断是否在多边形里面
def is_in_polygon(p,polygon):
    x_num = 0
    for i in range(len(polygon)-1):
        if isRayIntersectsSegment(p,polygon[i],polygon[i+1]):
            x_num += 1
    return x_num % 2 == 1




@app.route('/cfg',methods=['POST','GET'])
def set_cfg():
    global cfg
    if request.method == 'POST':
        cfg = request.json['data']
        cfg.append(cfg[0])# 这里多边形闭环(如果已经闭环,请注释)
        return 'ok'
    else:
        return 'wrong requests'
        
@app.route('/p',methods=['POST'])
def p_in_polygon():
    p = request.json
    f = is_in_polygon(p,cfg)
    return json.dumps({"in":f})

if __name__ == '__main__':
    #app.debug = True
    app.run('0.0.0.0',3000)
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值