如何获取pcl::VoxelGrid每个体素的点数量,初始化报错如何解决
报错诱因
pcl::VoxelGridCovariance类的模板参数要求传入单点数据类型,例如pcl::PointXYZ、pcl::PointXYZI等。你代码中传入的pcl::PCLPointCloud2是PCL定义的点云序列化存储结构,不属于单点点类型,PCL的类型特质系统没有为它注册对应的字段元信息,因此编译时触发了POINT_TYPE_NOT_PROPERLY_REGISTERED相关的类型校验错误,后续的继承成员访问错误也都是模板参数不匹配导致的派生类实例化失败衍生问题。
可行方案
方案1:修正VoxelGridCovariance用法实现需求
第一步先将pcl::PCLPointCloud2格式的点云转换为具体点类型的点云,再使用对应点类型实例化VoxelGridCovariance,示例代码如下:
#include <pcl/filters/voxel_grid_covariance.h> #include <pcl/conversions.h> // 假设你的输入是pcl::PCLPointCloud2格式,变量名为input_cloud2 pcl::PointCloud<pcl::PointXYZ>::Ptr cloud(new pcl::PointCloud<pcl::PointXYZ>); pcl::fromPCLPointCloud2(input_cloud2, *cloud); // 实例化体素网格 pcl::VoxelGridCovariance<pcl::PointXYZ> vg; vg.setInputCloud(cloud); vg.setLeafSize(0.05f, 0.05f, 0.05f); // 按需求设置体素边长,单位与点云坐标一致 pcl::PointCloud<pcl::PointXYZ> voxel_output; vg.filter(voxel_output); // 方式1:遍历所有非空体素获取点数 const auto& leaf_map = vg.getLeaves(); for (const auto& entry : leaf_map) { // entry.first为体素的三维索引(Eigen::Vector3i),entry.second为对应leaf实例 int voxel_point_num = entry.second.getPointCount(); // 自行处理点数逻辑 } // 方式2:查询指定空间坐标所属体素的点数 Eigen::Vector3f query_pos(1.2f, 3.4f, 0.5f); const pcl::VoxelGridCovariance<pcl::PointXYZ>::Leaf* target_leaf = vg.getLeaf(query_pos); if (target_leaf != nullptr) { int query_point_num = target_leaf->getPointCount(); }
方案2:轻量自定义实现体素点数统计
如果不需要协方差计算相关的额外能力,可以直接手动实现体素统计,没有额外开销,逻辑更可控:
// 定义体素索引哈希(也可直接用std::map<Eigen::Vector3i, int>存储) struct VoxelHash { size_t operator()(const Eigen::Vector3i& idx) const { return ((idx.x() * 73856093) ^ (idx.y() * 19349663) ^ (idx.z() * 83492791)) % 10000019; } }; float leaf_size = 0.05f; std::unordered_map<Eigen::Vector3i, int, VoxelHash> voxel_count; for (const auto& pt : *cloud) { // 计算点所属的体素索引 Eigen::Vector3i idx( static_cast<int>(std::floor(pt.x / leaf_size)), static_cast<int>(std::floor(pt.y / leaf_size)), static_cast<int>(std::floor(pt.z / leaf_size)) ); voxel_count[idx]++; } // 遍历voxel_count即可拿到所有体素对应的点数量
内容的提问来源于stack exchange,提问作者Chufan Jiang
相关产品推荐
相关产品推荐

