【问题标题】:euclidean distance for each point in a point cloud点云中每个点的欧几里得距离
【发布时间】:2019-05-07 09:33:35
【问题描述】:

我想计算一个点云中每个点与第二个点云中所有其他点之间的最小欧式距离。
我的点云被命名为 pc1 和 pc2。 Np 是每个点的法线向量矩阵。

到目前为止,我使用以下代码:

dist = zeros(size(pc2,1),1);
sign = zeros(size(pc2,1),1);

for i = 1:size(pc2,1)
     d = (pc1(:,1)-pc2(i,1)).^2 + (pc1(:,2)-pc2(i,2)).^2 + (pc1(:,3) - pc2(i,3)).^2;
    [d, ind] = min(d);
    dist(i,1) = sqrt(d);
    sign(i,1) = Np(ind,:)*(pc2(i,:)-pc1(ind,:))';
end

带有“符号”的最后一位来自this 纸。我添加它是因为我想知道我的点是在另一个点云内部还是外部。 (我从 STL 文件中收到点云,它们代表表面)

由于我正在处理大约 200.000 到 3.000.000 点的相当大的点云,因此计算需要一段时间,我想知道是否有人可以建议对我的代码进行优化。 也许它可以被矢量化,但我没有看到它。
欢迎您提出所有建议。提前感谢您的时间和帮助。

编辑:只是为了清除。我的点云矩阵中的每一行都是一个点。第一列是 x-,第二列是 y-,第三列是 z-值。

【问题讨论】:

    标签: matlab point-clouds euclidean-distance


    【解决方案1】:

    您当然可以以矢量化形式执行此操作,使用pdist2min,如下所示。

    dmat = pdist2(pc1, pc2);
    [dist, ind] = min(dmat);
    

    我相信以下内容适用于签名,但您应该验证结果。可能需要根据矩阵形状稍微调整。

    sign = sum(Np(ind,:).*(pc2-pc1(ind,:)), 2);
    

    【讨论】:

    • 不幸的是,这不适用于我要计算的点数。 pdist2 想要创建一个大小为 90 GB 的数组。
    • 我不知道有一种方法可以同时比较那么多点的距离。即使您不能一次完成所有事情,也许您可​​以将 pc2 划分为可管理的块。例如,如果您有 100 万个点,请创建一个重复 100 次的循环,并使用上面的矢量化代码考虑每个循环 10,000 个点。这仍然应该比单独循环遍历每个点要快得多,并且您可以对其进行调整以使您在内存限制范围内工作。
    • 感谢您的建议。我将尝试将我的点云分解为可管理的垃圾。
    • 嗨,马特,我只是想让你知道,它就像一个魅力。我沿 z 轴将点云切成块。现在它比以前快了很多(大约 10 倍)。再次感谢。
    【解决方案2】:

    另一种选择是使用KdTree's。这也是PCL的做法。

    使用这种方法,您基本上可以从参考点云创建一个 KdTree,然后对查询点云中的每个点进行最近邻搜索。 p>

    这种方法将比蛮力方法快很多。

    【讨论】:

      猜你喜欢
      • 2011-01-29
      • 2014-10-27
      • 1970-01-01
      • 2018-08-05
      • 2015-01-16
      • 1970-01-01
      • 2013-03-02
      相关资源
      最近更新 更多