以下是完善后的C++代码,用于对点云ply文件进行欧式聚类,并将聚类索引结果保存到clusterIndices中:

for (int j = 0; j < clouds[i]->size(); j++)
{
    // 以点j为中心进行聚类(xj, yj, zj),设置半径为r,进行欧式聚类,这里会得到骨架点个数的簇,所以也要创建指针容器
    pcl::PointCloud<pcl::PointXYZ>::Ptr yq = yenn[j];
    pcl::PointXYZ centroid1;
    centroid1.x = clouds[i]->points[j].x;
    centroid1.y = clouds[i]->points[j].y;
    centroid1.z = clouds[i]->points[j].z;

    pcl::EuclideanClusterExtraction<pcl::PointXYZ> ec;
    ec.setClusterTolerance(r); // 设置聚类的半径
    ec.setMinClusterSize(1); // 设置聚类的最小点数
    ec.setMaxClusterSize(clouds[i]->size()); // 设置聚类的最大点数
    ec.setSearchMethod(tree);
    ec.setInputCloud(clouds[i]);
    // 使用 setInputCloud 方法设置输入点云
    ec.setInputCloud (clouds[i]);
    // 使用 indices_  成员变量指定要进行聚类的点云索引
    pcl::PointIndices::Ptr yq_indices (new pcl::PointIndices);
    yq_indices->indices.push_back(j);
    ec.setIndices(yq_indices);
    std::vector<pcl::PointIndices> clusterIndices;
    ec.extract(clusterIndices);

    // Output the indices of the clusters
    for (const auto& indices : clusterIndices) // 遍历储存的所有类的索引
    {
        pcl::PointCloud<pcl::PointXYZ>::Ptr cluster7(new pcl::PointCloud<pcl::PointXYZ>);
        for (const auto& index : indices.indices) // 循环遍历一个类里所有点的索引将其加入点云指针
        {
            cluster7->push_back(clouds[i]->points[index]); // 将索引对应的点加入到这个类的指针中
        }
        yemm.push_back(cluster7); // 得到的一个类通过尾插法将其指针加入指针容器yenn,所以一片叶子的多个指针表示为clusters[i]
    }
}

代码解释:

  1. 创建欧式聚类对象: pcl::EuclideanClusterExtraction<pcl::PointXYZ> ec;
  2. 设置聚类参数:
    • ec.setClusterTolerance(r); 设置聚类半径
    • ec.setMinClusterSize(1); 设置最小聚类点数量
    • ec.setMaxClusterSize(clouds[i]->size()); 设置最大聚类点数量
    • ec.setSearchMethod(tree); 设置搜索方法,可以使用kd-tree加速
    • ec.setInputCloud(clouds[i]); 设置输入点云
    • ec.setIndices(yq_indices); 设置聚类的起点
  3. 执行聚类: ec.extract(clusterIndices); 将聚类结果保存在 clusterIndices
  4. 遍历聚类结果: 代码中使用循环遍历 clusterIndices ,并将每个聚类结果保存到新的点云对象中。

注意:

  • r 是聚类半径,需要根据实际情况调整
  • tree 是预先建立的搜索树,可以为空,但使用搜索树可以提高效率
  • yq_indices 是一个 pcl::PointIndices 对象,用于指定要进行聚类的点云索引,这里我们只选择了点云中的第 j 个点作为起点。
C++ PCL欧式聚类:以指定点为起点并保存聚类索引

原文地址: http://www.cveoy.top/t/topic/fEfq 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录