1

z我的目标是通过仅返回每个非重叠网格单元内具有最高值的点来实现一个 python 函数来细化激光雷达点云。

每个网格单元只返回一个点。

我在 python 中编写了以下函数,但与 MATLAB 中的类似实现相比,处理示例文件需要更长的时间(大约慢 10 倍)。

我可以更改功能以加快速度吗?

在函数中,data 是一个 Nx3 数组,csize 是非重叠网格单元的大小。

def pcthin(data, csize):
 md = data
 xx = np.arange(np.min(md[:,0]), csize*(np.ceil(max(md[:,0]))/csize), csize)
 yy = np.arange(np.min(md[:,1]), csize*(np.ceil(max(md[:,1]))/csize), csize)
 X,Y = np.meshgrid(xx,yy, sparse=False, indexing='xy')

 thindata = np.zeros_like(data)
 k = 0
 xf = X.flatten()
 yf = Y.flatten()
 for x,y in zip(xf,yf):
    tf1 = np.logical_and(md[:,0] > x, md[:,0] <= x + csize)
    tf2 = np.logical_and(md[:,1] > y, md[:,1] <= y + csize)
    tf = np.logical_and(tf1,tf2)
    if any(tf):
        dtx = md[tf,:]
        ix = np.argmax(dtx[:,2])
        thindata[k,:] = dtx[ix,:]

        k = k + 1

return thindata[0:k+1,:]
4

1 回答 1

1

更新关于代码的答案

问题是在 Python 中天真的“for”循环很慢,而且你的代码有一个很大的 for 循环。为了获得 Python 的最大速度,您应该尝试“矢量化”您的代码或使用numba并尝试使用 for 循环重新编写代码,就像您编写 C++ 一样。


旧答案

因此,如果我正确理解您的问题,这就是您可以使用https://github.com/daavoo/pyntcloud完成它的方法


加载示例点云:

from pyntcloud import PyntCloud
cloud = PyntCloud.from_file("tests/data/sphere.ply")

看起来像这样:

领域


然后你必须建立一个不重叠的单元格(在 pyntcloud 中称为 voxelgrid)。

这里是您如何指定沿每个轴的单元格大小size_xsize_y

voxelgrid_id = cloud.add_structure("voxelgrid", size_x=10, size_y=10)

体素网格如下所示:

体素网格


最后,您可以通过选择每个单元格的最高点来获得新的点云:

thinned_cloud = cloud.get_sample(
    "voxelgrid_highest",
    voxelgrid_id=voxelgrid_id,
    as_PyntCloud=True)

看起来像这样:

变薄的云

您可以访问新细化点云的 xyz 值,如下所示:

data = thinned_cloud.xyz

这在内部使用 pandas.groupby ,与您发布的代码相比,这应该是一个速度改进。但是,如果这仍然不够快,我建议您尝试https://numba.pydata.org/

在https://github.com/daavoo/pyntcloud/blob/master/pyntcloud/utils/numba.py中有一些示例操作可能对您有用

于 2018-06-09T19:08:59.320 回答