pcl里面的RoPs特征(Rotational Projection Statistics)

这次我们将使用pcl::ROPSEstimation这个类来导出点的特征。

下面是这个方法的特征提取方式。有一个网格和一个点集可以让我们来执行一些简单的操作。第一步,对于一个给定的兴趣点局部的表面将会被削平。局部表面包含了在半径内的点和三角形。对于给定的局部表面LRF将被计算。LRF是向量的3个组之一。真正重要的是使用那些具有旋转不变的向量。为了做到这一点,我们把感兴趣的点作为原点来做转换,再这之后我们旋转局部表面,以至于LRF向量关于Ox,Oy,Oz坐标轴对称。完成这些后,我们开始了特征导出。对于每个Ox,Oy,Oz坐标轴,我们会把这些这些坐标轴作为当前的坐标轴。

1.局部表面通过一个给定的角度在当前的坐标轴进行旋转。

2.把局部表面投影成3个平面XY,XZ和YZ.

3.对于每个投影分布矩阵,这个矩阵将展示怎么样把把点分到不同的容器里面。容器的数量代表了矩阵的维度和算法的参数。

4.每个分布矩阵的中心矩将会被计算。M11,M12,M21,M22,E。E是信息熵。

5.计算值将会组成子特征。

 

我们把上面这些步骤进行多次迭代。不同坐标轴的子特征将组成RoPS描述器。

下面是代码

我们首先要找到目标模型

points 包含点云

indices 点的下标

triangles包含了多边形

#include <pcl/features/rops_estimation.h>
#include <pcl/io/pcd_io.h>

int main (int argc, char** argv)
{
  if (argc != 4)
    return (-1);

  pcl::PointCloud<pcl::PointXYZ>::Ptr cloud (new pcl::PointCloud<pcl::PointXYZ> ());
  if (pcl::io::loadPCDFile (argv[1], *cloud) == -1)
    return (-1);

  pcl::PointIndicesPtr indices = boost::shared_ptr <pcl::PointIndices> (new pcl::PointIndices ());
  std::ifstream indices_file;
  indices_file.open (argv[2], std::ifstream::in);
  for (std::string line; std::getline (indices_file, line);)
  {
    std::istringstream in (line);
    unsigned int index = 0;
    in >> index;
    indices->indices.push_back (index - 1);
  }
  indices_file.close ();

  std::vector <pcl::Vertices> triangles;
  std::ifstream triangles_file;
  triangles_file.open (argv[3], std::ifstream::in);
  for (std::string line; std::getline (triangles_file, line);)
  {
    pcl::Vertices triangle;
    std::istringstream in (line);
    unsigned int vertex = 0;
    in >> vertex;
    triangle.vertices.push_back (vertex - 1);
    in >> vertex;
    triangle.vertices.push_back (vertex - 1);
    in >> vertex;
    triangle.vertices.push_back (vertex - 1);
    triangles.push_back (triangle);
  }

  float support_radius = 0.0285f;
  unsigned int number_of_partition_bins = 5;
  unsigned int number_of_rotations = 3;

  pcl::search::KdTree<pcl::PointXYZ>::Ptr search_method (new pcl::search::KdTree<pcl::PointXYZ>);
  search_method->setInputCloud (cloud);

  pcl::ROPSEstimation <pcl::PointXYZ, pcl::Histogram <135> > feature_estimator;
  feature_estimator.setSearchMethod (search_method);
  feature_estimator.setSearchSurface (cloud);
  feature_estimator.setInputCloud (cloud);
  feature_estimator.setIndices (indices);
  feature_estimator.setTriangles (triangles);
  feature_estimator.setRadiusSearch (support_radius);
  feature_estimator.setNumberOfPartitionBins (number_of_partition_bins);
  feature_estimator.setNumberOfRotations (number_of_rotations);
  feature_estimator.setSupportRadius (support_radius);

  pcl::PointCloud<pcl::Histogram <135> >::Ptr histograms (new pcl::PointCloud <pcl::Histogram <135> > ());
  feature_estimator.compute (*histograms);

  return (0);
}

 

上面是指定下标点的RoPS特征计算的地方

 std::vector <pcl::Vertices> triangles;
  std::ifstream triangles_file;
  triangles_file.open (argv[3], std::ifstream::in);
  for (std::string line; std::getline (triangles_file, line);)
  {
    pcl::Vertices triangle;
    std::istringstream in (line);
    unsigned int vertex = 0;
    in >> vertex;
    triangle.vertices.push_back (vertex - 1);
    in >> vertex;
    triangle.vertices.push_back (vertex - 1);
    in >> vertex;
    triangle.vertices.push_back (vertex - 1);
    triangles.push_back (triangle);
  }

上面是加载关于多边形的信息的。你可以取代信息用下面的代码来进行三角划分,如果你只有点云没有网格图。

 float support_radius = 0.0285f;
  unsigned int number_of_partition_bins = 5;
  unsigned int number_of_rotations = 3;

上面的这些代码定义了重要的算法参数,局部表面裁剪支持的半径,以及用于组成分布矩阵的容器的数量和旋转的次数。最后的参数将影响描述器的长度。

 pcl::search::KdTree<pcl::PointXYZ>::Ptr search_method (new pcl::search::KdTree<pcl::PointXYZ>);
  search_method->setInputCloud (cloud);


上面设置了搜索方法。

  pcl::ROPSEstimation <pcl::PointXYZ, pcl::Histogram <135> > feature_estimator;
  feature_estimator.setSearchMethod (search_method);
  feature_estimator.setSearchSurface (cloud);
  feature_estimator.setInputCloud (cloud);
  feature_estimator.setIndices (indices);
  feature_estimator.setTriangles (triangles);
  feature_estimator.setRadiusSearch (support_radius);
  feature_estimator.setNumberOfPartitionBins (number_of_partition_bins);
  feature_estimator.setNumberOfRotations (number_of_rotations);
  feature_estimator.setSupportRadius (support_radius);

上面是实例化类的地方。它包含了两个参数

PointInT:输入点的类型

PointOutT:输出点的类型

最终我们需要进行特征计算

  pcl::PointCloud<pcl::Histogram <135> >::Ptr histograms (new pcl::PointCloud <pcl::Histogram <135> > ());
  feature_estimator.compute (*histograms);

然后运行

./rops_feature points.pcd indices.txt triangles.txt

 

你可能感兴趣的:(pcl里面的RoPs特征(Rotational Projection Statistics))