zoukankan      html  css  js  c++  java
  • points outline extraction从二维点集提取外轮廓线(Delaunay三角网 Alpha Shape算法)

    import numpy as np
    import matplotlib.pyplot as plt
    from mpl_toolkits.mplot3d import Axes3D
    from scipy.spatial import Delaunay
    from sklearn.neighbors import KDTree
    
    # Widyaningrum E , Peters R Y , Lindenbergh R C . Building outline extraction from als point clouds using medial axis transform descriptors[J]. Pattern Recognition, 2020:107447.
    
    def plot_circle(centers,rs,ax):
        N = centers.shape[0]
        for i in range(N):
            theta = np.arange(0, 2*np.pi, 0.01)
            x = centers[i,0] + rs[i] * np.cos(theta)
            y = centers[i,1] + rs[i] * np.sin(theta)
            ax.plot(x, y, 'b-', alpha=0.1)
    
    def edge_check_vaild(e,tree,r,err):
        xp = e[0]
        xq = e[1]
        L = np.sqrt(np.dot(xq-xp,xq-xp))
        if L > 2*r:
            return False, -1
        vec = (xq-xp)/L# the vector from p to q
        normal = np.array([vec[1], -vec[0]])
        c1 = (xp + xq) / 2 + normal * np.sqrt(r**2-(L/2)**2)
        c2 = (xp + xq) / 2 - normal * np.sqrt(r**2-(L/2)**2)
        c = np.array([c1, c2])
        count = tree.query_radius(c, r=r+err, return_distance=False, count_only=True, sort_results=False)
        if count[0] <= 2:
            return True, c[0]
        elif count[1] <= 2:
            return True, c[1]
        else:
            return False, -1
    
    
    def boundary_extract(points, alpha, err=10e-3):
        """
        Here, parameter err was place, because there are errors when calculating distance
        meanwhile, this err was different for different scaling 2D point cloud
        so, a parameter was placed here to considering the calculation errors
        """
        R = 1 / alpha
        pts = np.copy(points)
        tree = KDTree(pts, leaf_size=2)
        tri = Delaunay(pts)
        s = tri.simplices
        N = s.shape[0]
        i = 0
        edges = []
        centers = []
        while i <= N - 1:
            if s[i, 0] == -1:
                i = i + 1
                continue
            p3 = s[i]
            e1 = np.array([points[p3[0], :], points[p3[1], :]])
            e2 = np.array([points[p3[1], :], points[p3[2], :]])
            e3 = np.array([points[p3[0], :], points[p3[2], :]])
            e = [e1, e2, e3]
            for j in range(3):
                flag, center = edge_check_vaild(e[j], tree, R, err)
                if flag:
                    edges.append(e[j])
                    centers.append(center)
            nb = tri.neighbors[i]
            nb_valid = nb[nb != -1]
            #nb_valid_num = nb_valid.shape[0]
            #s[nb_valid] = -1
            i = i + 1
        return edges, centers
    
    
    def show_edge(edges, points, circle=None, r=None):
        fig = plt.figure()
        ax = fig.add_subplot(111)
        ax.scatter(*zip(*points), s=4, c='k')
        for i in range(len(edges)):
            ax.plot(*zip(*edges[i]), '-r')
        if circle is not None:
            plot_circle(circle, r, ax)
        plt.show()
    
    
    if __name__ == "__main__":
        pts = np.random.rand(200, 2)# 随机生成10个2维点
        alpha = 6
        edges, centers = boundary_extract(pts, alpha, err=10e-5)
        # show_edge(edges, pts, circle=np.array(centers), r=np.ones(len(centers))/alpha)
        show_edge(edges, pts)
        print("over!!!")
    个人学习记录
  • 相关阅读:
    冲刺第一天
    Nacos微服务体系配置管理
    Nacos配置中心客户端程序
    Nacos配置中心最佳实践
    SpringCloud2020整合Nacos-Bootstrap配置不生效的解决
    18.SpringCloud Alibaba Nacos服务注册和配置中心
    17、SpringCloud Alibaba入门简介
    SpringBoot热部署
    SpringBoot请求处理-常用参数注解使用
    5、创建springcloud alibaba工程
  • 原文地址:https://www.cnblogs.com/jeshy/p/15083384.html
Copyright © 2011-2022 走看看