• octomap点云压缩


    如果点云文件比较大,可以利用octomap库对点云进行压缩。

    octomap以八叉树结构对点云进行组织,是一种有损压缩,定义不同的分辨率可以保存不同尺度的数据。

    这里以rabbit.pcd文件为例,分别将点云保存为文本格式(.txt),二进制格式(.bin),八叉树格式(.ot),八叉树二进制模式(.bt),对比存为不同格式文件的大小。

    程序运行需要安装pcl和octomap,示例如下:

    #include <iostream>
    #include <vector>
    #include <pcl/io/pcd_io.h>
    #include <pcl/point_types.h>
    #include <octomap/octomap.h>
    #include <octomap/OcTree.h>
    
    using namespace std;
    
    class PointCloudInfo
    {
    public:
        typedef boost::shared_ptr<PointCloudInfo> Ptr;            /*!< Point cloud information shared point */
        typedef boost::shared_ptr<const PointCloudInfo> ConstPtr; /*!< Point cloud information shared point (const)*/
    
        pcl::PointCloud<pcl::PointXYZ>::Ptr cloud; /*!< Pcl point cloud */
        double octo_min_x{ 0 };                    /*!< Minimum x-axis value of octomap */
        double octo_min_y{ 0 };                    /*!< Minimum y-axis value of octomap */
        double octo_min_z{ 0 };                    /*!< Minimum z-axis value of octomap */
        double octo_max_x{ 0 };                    /*!< Maximum x-axis value of octomap */
        double octo_max_y{ 0 };                    /*!< Maximum y-axis value of octomap */
        double octo_max_z{ 0 };                    /*!< Maximum z-axis value of octomap */
        double octo_resol{ 0 };                    /*!< Octomap Resolution */
    };
    
    struct xyz
    {
        float x;
        float y;
        float z;
    };
    
    int main()
    {
    
        pcl::PointCloud<pcl::PointXYZ> cloud;
        pcl::io::loadPCDFile<pcl::PointXYZ> ( "rabbit.pcd", cloud );    
    
        octomap::OcTree tree( 0.001 );
        vector<xyz> vp;
        xyz m_p;
        FILE *fp = fopen("rabbit.txt","w");        
    
        for (auto p:cloud.points)
        {
            m_p.x = p.x;
            m_p.y = p.y;
            m_p.z = p.z;
            vp.emplace_back(m_p);
    
            tree.updateNode( octomap::point3d(p.x, p.y, p.z), true );
            fprintf(fp,"%f %f %f
    ",p.x,p.y,p.z);
        }
        fclose(fp);
    
        fp = fopen("rabbit.bin","wb");
        fwrite(&vp[0],vp.size()*sizeof(xyz),1,fp);
        fclose(fp);
    
        tree.updateInnerOccupancy();
        tree.write("rabbit.ot");
        tree.writeBinary("rabbit.bt");
    
        ///////////////////////////read bt///////////////////////////////////////
        octomap::OcTree octo_tree(0.001);
        octo_tree.readBinary("rabbit.bt");
        
        PointCloudInfo::Ptr pc_info(new PointCloudInfo());
        octo_tree.getMetricMin(pc_info->octo_min_x, pc_info->octo_min_y, pc_info->octo_min_z);
        octo_tree.getMetricMax(pc_info->octo_max_x, pc_info->octo_max_y, pc_info->octo_max_z);
        pc_info->octo_resol = octo_tree.getResolution();
    
    
        pc_info->cloud.reset(new pcl::PointCloud<pcl::PointXYZ>());
        pcl::PointXYZ point;
        for (octomap::OcTree::leaf_iterator it = octo_tree.begin_leafs(); it != octo_tree.end_leafs(); ++it)
        {
            if (it != nullptr && octo_tree.isNodeOccupied(*it))
            {
                point.x = static_cast<float>(it.getX());
                point.y = static_cast<float>(it.getY());
                point.z = static_cast<float>(it.getZ());
                pc_info->cloud->push_back(point);
            }
        }
    
        return 0;
    }

    保存后的ot或bt文件可以利用octovis查看,输入octovis rabbit.bt即可。

    下表是不同文件的大小:

    rabbit.pcd 1.2M
    rabbit.txt 1.0M
    rabbit.bin 431.4K
    rabbit.ot 282.8K
    rabbit.bt 44.2K

    可以看出bt文件压缩率还是很高的,虽然是有损压缩,不过在很多情况下已经够用了。

  • 相关阅读:
    Java并发初识
    go交叉编译
    MRC与ARC混合开发配置
    Hibernate配置文件
    LEFT JOIN重复数据
    Ext.ViewPort布局
    Hibernate学习映射文件
    AjaxMethod方法
    DataBinder
    subsonic 获取记录数量
  • 原文地址:https://www.cnblogs.com/tiandsp/p/12819031.html
Copyright © 2020-2023  润新知