区域生长分割 Region growing segmentation(一)

理论入门

首先要用各点的曲率值对点进行排序,因为一个区域要从它曲率最小值的点开始生长。因为从曲率最小点可以定位到平坦的区域,而从最平坦区域的增长可以减少分割区域的数量。

因此先对点云进行一下排序。在云中存在未标记(这个标记我认为是人工手动标记)的点之前,算法会选择具有最小曲率值的点并开始该区域的增长。此过程如下:      

  • 选择的点被添加到称为种子的集合中。

  • 对于每个种子点算法找到其相邻点。

    • (1)测试每个相邻点的法线与当前种子点法线之间的角度。如果角度小于阈值,则将当前点添加到当前区域。
    • (2)测试完角度之后,再测试每个相邻点的曲率值。如果曲率小于阈值,则将该点添加到种子集合中。
    • (3)从种子集合中除去当前的种子。

(1)中,因为当前的选取的种子点就是曲率最小的点了,所以就先测与一下周围点法线的夹角,如果角度不大的话(角度小于指定阈值),就进行区域生长。先假设最初的种子点周围的相邻点巧了嘿,都满足这个条件,都被种子点发展过来了。

(2)好了,经过(1)可以看到,最初的种子点已经尽力自己最大的努力,最多也就才能把它周围的所有点都发展来(归到生长区域),再靠外的点它接触不到了。然而我们生长算法算是贪心的吧,还想继续扩大自己领地(继续生长)。

这时候就委屈一下了,曲率最小的点只有一个,只能退而求其次。现在开始睁一只眼闭一只眼,规定了一个曲率的阈值。只要是初始种子点的发展来的,就是(1)中新生长的区域只要满足曲率小于规定的阈值,就可以把他们加入到种子点集合中(相当于提高了权限哈)。

现在假设,哎,刚好有一个点满足相邻点曲率的条件(也可以是多个点满足)!把这个点加入到种子集合中(有了接班人相当于)。走到(3)把最初种子点去除,然而还有刚才(2)中新加入到种子点集合中的新成员。再把它作为选定的种子点重复(1)。循环往复,直到遇到了种子点集合为空的情况停止生长。

现在假设刚才新发展来的相邻点全都不符合了曲率条件。这。。。走到(3)就要把最初种子点去除了,种子集合中也就没了种子点,成了空集。则意味着算法已经完全生长了该区域并且要从头开始重复该过程。可以在下面找到所述算法的伪代码。

Inputs:

  • Point cloud = \{P\}
  • Point normals = \{N\}
  • Points curvatures = \{c\}
  • Neighbour finding function \Omega(.)
  • Curvature threshold c_{th}
  • Angle threshold \theta_{th}

Initialize:

  • Region list {R}\leftarrow{\O}
  • Available points list \{A\}\leftarrow\{1,...,|P|\}

Algorithm:

  • While \{A\} is not empty do

    • Current region \{R_c\}\leftarrow{\O}

    • Current seeds \{S_c\}\leftarrow{\O}

    • Point with minimum curvature in \{A\}\rightarrow P_{min}

    • \{S_c\}\leftarrow\{S_c\}\cup P_{min}

    • \{R_c\}\leftarrow\{R_c\}\cup P_{min}

    • \{A\}\leftarrow\{A\}\setminus P_{min}     注:这里应该是从点集A剔除的意思

    • for i=0 to size ( \{S_c\} ) do

      • Find nearest neighbours of current seed point \{B_c\}\leftarrow\Omega(S_c\{i\})

      • for j=0 to size ( \{B_c\} ) do

        • Current neighbour point P_j\leftarrow B_c\{j\}

        • If \{A\} contains P_j and cos^{-1}(|(N\{S_c\{i\}\},N\{S_c\{j\}\})|)<\theta_{th} then

          • \{R_c\}\leftarrow\{R_c\}\cup P_j

          • \{A\}\leftarrow\{A\}\setminus P_j

          • If c\{P_j\}<c_{th} then

            • \{S_c\}\leftarrow\{S_c\}\cup P_j
          • end if

        • end if

      • end for

    • end for

    • Add current region to global segment list \{R\}\leftarrow\{R\}\cup\{R_c\}

  • end while
  • Return \{R\}

 

  • 2
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
区域生长算法是一种点云分割方法,它通过将相邻的点聚合成区域分割点云。以下是一个基于MATLAB的点云分割区域生长算法的实现。 首先,我们需要读取点云数据。在本例中,我们将使用一个简单的点云数据集,该数据集包含一个球形物体和一个立方体物体。 ``` % 读取点云数据 pc = pcread('example.pcd'); ``` 接下来,我们将定义一些区域生长算法的参数。这些参数包括: - `seedPoint`:种子点,用于启动区域生长算法。 - `distanceThreshold`:距离阈值,用于确定哪些点应该被聚合成一个区域。 - `normalThreshold`:法向量阈值,用于确定哪些点应该被聚合成一个区域。 - `maxNumPoints`:最大点数,用于限制每个区域的大小。 ``` % 定义区域生长算法参数 seedPoint = [0, 0, 0]; distanceThreshold = 0.01; normalThreshold = 0.8; maxNumPoints = 1000; ``` 接下来,我们将使用 `pcsegdist` 函数来执行区域生长算法。该函数需要传入点云数据、种子点、距离阈值、法向量阈值和最大点数等参数。该函数将返回一个包含每个点所属区域编号的向量。 ``` % 执行区域生长算法 labels = pcsegdist(pc, seedPoint, distanceThreshold, normalThreshold, maxNumPoints); ``` 最后,我们将使用 `pcshow` 函数来可视化点云数据和分割结果。我们将使用不同的颜色来表示不同的区域。 ``` % 可视化点云数据和分割结果 figure; pcshow(pc.Location, labels); title('Point Cloud Segmentation Using Region Growing Algorithm'); xlabel('X'); ylabel('Y'); zlabel('Z'); ```
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值