栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Python

python判断某点是否在某个多边形(区域)内

Python 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

python判断某点是否在某个多边形(区域)内

判断某个点是不是在某个区域内,用到的一个方法是这个点往右延伸成线段,然后计算这个线段与多边形区域线段交点的个数,交点个数为奇数则该点在内。也可以是这个点往上,往下,往左,自己规定。

代码里用了cv来辅助看看有没有判断对,自行处理。

import cv2

def draw_img(point_list,point,is_in):
    # 将点依次连接,并将需要判断的点画出来
    img_path = r'C:UsersAdministratorDesktopmytable.jpg'
    img = cv2.imread(img_path)
    img = cv2.resize(img, (700, 450))
    for i in range(len(point_list)-1):
        x1 = point_list[i][0]
        y1 = point_list[i][1]
        x2 = point_list[i+1][0]
        y2 = point_list[i+1][1]
        cv2.line(img,(x1,y1),(x2,y2),(0,255,255),2)
    xb = point_list[0][0]
    yb = point_list[0][1]
    xe = point_list[-1][0]
    ye = point_list[-1][1]
    cv2.line(img, (xb, yb), (xe, ye), (0, 255, 255), 2)
    if is_in:
        cv2.circle(img, point, 3, (0, 0, 0), 4)
    else:
        cv2.circle(img,point,3,(255,255,255),4)
    cv2.imshow('a',img)
    cv2.waitKey(2000)

def judge_line(point_line,point):
    #判断点往右延伸是否与线段相交,相交返回true,不想交返回false
    x = point[0]
    y = point[1]
    x1 = point_line[0][0]
    y1 = point_line[0][1]
    x2 = point_line[1][0]
    y2 = point_line[1][1]
    if y1 > y2: #确认在上方的点,用该点做减数来计算斜率
        ymax = y1
        xmax = x1
        ymin = y2
        xmin = x2
    else:
        ymax = y2
        ymin = y1
        xmax = x2
        xmin = x1
    if y >= ymax or y <= ymin: #点不在线段的垂直范围里不可能相交
        return False
    if x >= max(x1,x2): #点在线段的右侧也不可能相交
        return False
    k_line = 0
    k_point = 0
    if x1 == x2: #针对横坐标或纵坐标相等做的一些处理
        k_line = 100
    if y1 == y2:
        k_line = 0.01
    if k_line == 0:
        k_line = (ymax-ymin)/(xmax-xmin)
    if x == xmax:
        k_point = 100
    if y == ymax:
        k_point = 0.01
    if k_point == 0:
        k_point = (ymax-y)/(xmax-x)
    if k_line > 0: #线段斜率可能是正负,点可能在线段的左右侧,分类讨论
        if k_point < k_line:
            return True
        else:
            return False
    else:
        if k_point>0:
            return True
        else:
            if k_line > k_point:
                return True
    return False
def judge_in(point_list,point):
    # 该点向右的射线与多边形的交点数为奇数则在多边形内,偶数则在外
    # 遍历线段,比较y值,point的y处于线段y值中间则相交
    # 多边形坐标按下笔顺序,因为顺序不同,多边形围合的形状也不同,比如五个点,可以使五角星,也可是五边形
    # 在多边形内返回true,不在返回false
    num_intersect = 0 # 交点数
    num_intersect_vertex = 0 #点与顶点的纵坐标相同的数量,用一下方法纵坐标相同时会计算两次交点数(一个点是两个线段的顶点),最后减去(相当于只计算一次)
    for item in point_list:
        if item[1] == point[1]:
            num_intersect_vertex += 1
    x = point[0]
    y = point[1]
    for i in range(len(point_list)-1):
        point_line = [point_list[i],point_list[i+1]]
        if judge_line(point_line,point):
            num_intersect += 1
    xb = point_list[0][0] #首尾坐标的线段
    yb = point_list[0][1]
    xe = point_list[-1][0]
    ye = point_list[-1][1]
    point_lines = [(xb,yb),(xe,ye)]
    if judge_line(point_lines,point):
        num_intersect += 1
    print("与多变形交点的个数为:%d"%num_intersect)
    num_intersect -= num_intersect_vertex
    if num_intersect > 0 and num_intersect%2==1:
        return True
    else:
        return False


#线是黄色的,点在区域里则点是黑色,否则为白色
point_list = [(100,100),(100,300),(200,200)]
point = (150,200)
is_in = judge_in(point_list,point)
draw_img(point_list,point,is_in)

下面是几张效果图

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/997216.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号