PCL-IO输入输入模块

本文详细介绍了PCL库中关于3D数据的读写功能,包括点云数据格式如PCD、PLY、OBJ、STL等的处理,以及如何使用load和saveAPI读取和保存不同格式的3D文件。
摘要由CSDN通过智能技术生成

一、概述

PCL 库提供了一个模块用来对3D数据进行读写操作,这个库提供了一个模块:pcl_io库包含用于读取和写入文件以及从各种传感设备捕获点云的类和函数。每一个版本的函数接口可能有些差异,具体还是得去看官网的参考文档才能正确的使用。

我这里的环境

PCL版本: PCL 1.14.0-dev
编程语言:C++

在这里插入图片描述

二、点云数据格式

1. PCD 格式

参考链接:《太阳风暴》点云格式-PCD格式介绍

2. PLY 格式

3. OBJ 格式

4. STL 格式

5. OFF 格式

三、读取3D文件

1. API 总览

第一列是文件格式类型;第一行表头代表文件中的数据是什么内容、可以是点云、多边形mesh、材质。

PCL 为我们提供了针对于专门文件格式的读写API,就想 loadPCDFile、loadPLYFile等。也有提供了不区分格式的文件读取API,就像 load 函数一样。

pcl::PointCloudpcl::PCLPointCloud2pcl::PolygonMeshpcl::TextureMesh
PCD (ASCII/BINARY/COMPRESSED)loadPCDFileloadPCDFile
PLY (ASCII/BINARY)loadPLYFileloadPLYFileloadPLYFile
OBJ (ASCII)loadOBJFileloadOBJFileloadOBJFileloadOBJFile
IFSloadIFSFileloadIFSFileloadIFSFile
STL (ASCII/BINARY)loadPolygonFileSTL
VTKloadPolygonFileVTK
CSV/ASCIIvia pcl::ASCIIReadervia pcl::ASCIIReader
Automatic format detectionloadloadloadload

这个就需要看这个PCL的源代码怎么写的,一般我只用 load 函数,我们看看PCL load 函数的实现就明白了。其实 load 函数就是对 load**File函数的一些列的封装,暂时支持的格式也只有上面提到的pcd、ply等格式之类的。

namespace pcl
 {
   namespace io
   {
     template<typename PointT> int
     load (const std::string& file_name, pcl::PointCloud<PointT>& cloud)
     {
       pcl_fs::path p (file_name.c_str ());
       std::string extension = p.extension ().string ();
       int result = -1;
       if (extension == ".pcd")
         result = pcl::io::loadPCDFile (file_name, cloud);
       else if (extension == ".ply")
         result = pcl::io::loadPLYFile (file_name, cloud);
       else if (extension == ".ifs")
         result = pcl::io::loadIFSFile (file_name, cloud);
       else if (extension == ".obj")
         result = pcl::io::loadOBJFile (file_name, cloud);
       else
       {
         PCL_ERROR ("[pcl::io::load] Don't know how to handle file with extension %s\n", extension.c_str ());
         result = -1;
       }
       return (result);
     }
   }
 }

2. 示例

最常用的格式就是 ply、obj、pcd格式的文件格式。下面简单看一下部分常用函数的定义:

#include <pcl/io/pcd_io.h>

template<typename PointT >
int pcl::io::loadPCDFile(const std::string & file_name, pcl::PointCloud< PointT > & cloud)	
#include <pcl/io/ply_io.h>
template<typename PointT >
int pcl::io::loadPLYFile(const std::string & file_name, pcl::PointCloud< PointT > & cloud)	

我主要用作读取点云数据。我也只会介绍点云相关的数据。

实例

#include <pcl/io/io.h>
#include <pcl/io/ply_io.h>
#include <pcl/point_cloud.h>

// 闭合写法
pcl::PointCloud<pcl::PointXYZ>::Ptr input_cloud (new pcl::PointCloud<pcl::PointXYZ>); //	输入点云的指针
pcl::io::loadPLYFile("pointcloud.ply", *input_cloud);	//	读取数据

// 分离写法
pcl::PointCloud<pcl::PointXYZ>::Ptr input_cloud;
input_cloud = pcl::PointCloud<pcl::PointXYZ>::Ptr(new pcl::PointCloud<pcl::PointXYZ>);	//	输入点云的指针
pcl::io::loadPLYFile("pointcloud.ply", *input_cloud);	//	读取数据

上面的 pcl::PointCloud<pcl::PointXYZ>::Ptr 其实就是宏定义的一个 share_ptr,我们其实也可以自己去管理这个类型的指针。

pcl::PointCloud<pcl::PointXYZ>::Ptr input_cloud;

// 宏定义
#include <pcl/point_cloud.h>
using Ptr = shared_ptr<PointCloud<PointT> >;
using ConstPtr = shared_ptr<const PointCloud<PointT> >;

官网完整的读取PCD文件

#include <iostream>
#include <pcl/io/pcd_io.h>
#include <pcl/point_types.h>

int main ()
{
  pcl::PointCloud<pcl::PointXYZ>::Ptr cloud (new pcl::PointCloud<pcl::PointXYZ>);
  
  if (pcl::io::loadPCDFile<pcl::PointXYZ> ("test_pcd.pcd", *cloud) == -1) //* load the file
  {
    PCL_ERROR ("Couldn't read file test_pcd.pcd \n");
    return (-1);
  }

  std::cout << "Loaded "
            << cloud->width * cloud->height
            << " data points from test_pcd.pcd with the following fields: "
            << std::endl;
            
  for (const auto& point: *cloud)
    std::cout << "    " << point.x
              << " "    << point.y
              << " "    << point.z << std::endl;
  return (0);
}

四、保存3D文件

1. API 总览

第一列是文件格式类型;第一行表头代表文件中的数据是什么内容、可以是点云、多边形mesh、材质。

这里面的 PCD ASCII 和 PCD BINARY 只是保存的数据格式不一样,内容是一样的,ASCII是用文本保存、BINARY则是以二进制保存数据。其他带这些也是以这个为原则保存的。

pcl::PointCloudpcl::PCLPointCloud2pcl::PolygonMeshpcl::TextureMesh
PCD ASCIIsavePCDFilesavePCDFile
PCD BINARYsavePCDFilesavePCDFile
PCD COMPRESSEDsavePCDFileBinaryCompressedvia pcl::PCDWriter
PLY ASCIIsavePLYFilesavePLYFilesavePLYFile
PLY BINARYsavePLYFilesavePLYFilesavePLYFileBinary
OBJ (ASCII)saveOBJFilesaveOBJFile
IFSsaveIFSFilesaveIFSFile
STL (ASCII/BINARY)savePolygonFileSTL
VTKsaveVTKFilesaveVTKFile or savePolygonFileVTK
Automatic format detectionsavesavesavesave

和 读取 文件的接口类似,save也是封装了以上的这些格式。

namespace pcl
 {
   namespace io
   { 
     template<typename PointT> int
     save (const std::string& file_name, const pcl::PointCloud<PointT>& cloud)
     {
       pcl_fs::path p (file_name.c_str ());
       std::string extension = p.extension ().string ();
       int result = -1;
       if (extension == ".pcd")
         result = pcl::io::savePCDFile (file_name, cloud, true);
       else if (extension == ".ply")
         result = pcl::io::savePLYFile (file_name, cloud, true);
       else if (extension == ".ifs")
         result = pcl::io::saveIFSFile (file_name, cloud);
       else
       {
         PCL_ERROR ("[pcl::io::save] Don't know how to handle file with extension %s\n", extension.c_str ());
         result = -1;
       }
       return (result);
     }
   }
}	

2. 示例

部分的接口如下,参数也是非常的明了,最后一个参数:是否以二进制保持数据,默认是以ASCII,也就是人看得到的数据保存。

#include <pcl/io/ply_io.h>
template<typename PointT >
int pcl::io::savePLYFile(const std::string &file_name, const pcl::PointCloud<PointT> &cloud,bool binary_mode = false)

#include <pcl/io/ply_io.h>
template<typename PointT >
int pcl::io::savePCDFile(const std::string &file_name, const pcl::PointCloud<PointT> &cloud, bool binary_mode = false) 	

知道这些API就可以去保持啦

#include <iostream>
#include <pcl/io/pcd_io.h>
#include <pcl/point_types.h>

int  main ()
{
  pcl::PointCloud<pcl::PointXYZ> cloud;

  // Fill in the cloud data
  cloud.width    = 5;
  cloud.height   = 1;
  cloud.is_dense = false;
  cloud.resize (cloud.width * cloud.height);

  for (auto& point: cloud)
  {
    point.x = 1024 * rand () / (RAND_MAX + 1.0f);
    point.y = 1024 * rand () / (RAND_MAX + 1.0f);
    point.z = 1024 * rand () / (RAND_MAX + 1.0f);
  }

  pcl::io::savePCDFile ("test_pcd.pcd", cloud);
  std::cerr << "Saved " << cloud.size () << " data points to test_pcd.pcd." << std::endl;

  for (const auto& point: cloud)
    std::cerr << "    " << point.x << " " << point.y << " " << point.z << std::endl;

  return (0);
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

太阳风暴

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值