Project1,简化了提取索引点云,点云合并

#include <pcl/visualization/cloud_viewer.h>
#include <iostream>//标准C++库中的输入输出类相关头文件。
#include <pcl/io/io.h>
#include <pcl/io/pcd_io.h>//pcd 读写类相关的头文件。
#include <pcl/io/ply_io.h>
#include <pcl/point_types.h> //PCL中支持的点类型头文件。
#include <pcl/octree/octree.h>
#include<fstream>
#include <string>
#include <vector>
#include <LasOperator.h>
#include <liblas/liblas.hpp>
#include <pcl/filters/passthrough.h>
#include <pcl/segmentation/region_growing.h>
#include <pcl/search/search.h>
#include <pcl/search/kdtree.h>
#include <pcl/features/normal_3d.h>using namespace std;void loadLasFile(string s, pcl::PointCloud<pcl::PointXYZRGB> &cloud);
void loadLasFile(string s, pcl::PointCloud<pcl::PointXYZRGB> &cloud) {/**读取las文件*/std::ifstream ifs(s, std::ios::in | std::ios::binary); // 打开las文件liblas::ReaderFactory f;liblas::Reader reader = f.CreateWithStream(ifs); // 读取las文件unsigned long int nbPoints = reader.GetHeader().GetPointRecordsCount();//获取las数据点的个数cloud.width = nbPoints;  //保证与las数据点的个数一致    cloud.height = 1;cloud.is_dense = false;cloud.points.resize(cloud.width * cloud.height);int i = 0;uint16_t r1, g1, b1;int r2, g2, b2;uint32_t rgb;while (reader.ReadNextPoint()) {// 获取las数据的x,y,z信息cloud.points[i].x = (reader.GetPoint().GetX());cloud.points[i].y = (reader.GetPoint().GetY());cloud.points[i].z = (reader.GetPoint().GetZ());//获取las数据的r,g,b信息r1 = (reader.GetPoint().GetColor().GetRed());g1 = (reader.GetPoint().GetColor().GetGreen());b1 = (reader.GetPoint().GetColor().GetBlue());r2 = ceil(((float)r1 / 65536)*(float)256);g2 = ceil(((float)g1 / 65536)*(float)256);b2 = ceil(((float)b1 / 65536)*(float)256);rgb = ((int)r2) << 16 | ((int)g2) << 8 | ((int)b2);cloud.points[i].rgb = *reinterpret_cast<float*>(&rgb);i++;}
}int main() {/**定义变量*///输入点云,轨迹线,保存种子pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZ>::Ptr trail(new pcl::PointCloud<pcl::PointXYZ>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud2(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr result(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr part(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr partSeed(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr seed(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr colored(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr tempCloud(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointXYZRGB tempPnt;//变量float x1, y1, x2, y2, a1, a2, a3, b11, b22, b3;//向量1,a,b为轨迹线上2点x1 = y1 = a1 = a2 = a3 = b11 = b22 = b3 = 0;x2 = 0; y2 = 1;float r = 1; //半径2float SmoothnessThreshold = 6;//3.0 0.37float CurvatureThreshold = 0.01;    //设置曲率的阈值1.0//读取输入电云cout << "读取点云" << endl;//pcl::io::loadPCDFile("sample100.pcd", *cloud);loadLasFile("sample100.las", *cloud);//读取轨迹线cout << "读取轨迹线" << endl;pcl::io::loadPCDFile("trail.pcd", *trail);cout << "原始点数: " << cloud->width << " \t" << "轨迹线点数: " << trail->width << endl;//cloud构建八叉树cout << "构建八叉树" << endl;float resolution = 128.0f;pcl::octree::OctreePointCloudSearch<pcl::PointXYZRGB> octree(resolution);octree.setInputCloud(cloud);octree.addPointsFromInputCloud();std::vector<int>pointIdx;std::vector<int>pointIdx1;/**开始循环*/for (size_t i = 0; i < trail->points.size() + 500; i += 20) {//cloud1->points.size()     cloud1->points.size()+500   500cout << "-------------------------------------------------------------" << endl;a1 = trail->points[i].x;a2 = trail->points[i].y;//cloud1->points[i+8].ya3 = trail->points[i].z;b11 = trail->points[i + 20].x;b22 = trail->points[i + 20].y;//cloud1->points[i+12].yb3 = trail->points[i + 20].z;x1 = a1 - b11;y1 = a2 - b22;float cosa = (x1*x2 + y1 * y2) / (sqrt(x1*x1 + y1 * y1) + sqrt(x2*x2 + y2 * y2));float sina = sqrt(1 - cosa * cosa);float range = r / sina;//分段Eigen::Vector3f n(-100000, min(a2, b22), -100000);//0xc0c0c0c0  0x3f3f3f3fEigen::Vector3f m(100000, max(a2, b22) - 0.001, min(a3, b3));octree.boxSearch(n, m, pointIdx);cout << i << " 这段有点数:" << pointIdx.size() << "\t";pcl::copyPointCloud(*cloud, pointIdx, *part);/*cout << "保存1.pcd成功" << endl;pcl::io::savePCDFileASCII("1.pcd", *part);*///分段切割种子点pcl::octree::OctreePointCloudSearch<pcl::PointXYZRGB> octree1(resolution);octree1.setInputCloud(part);octree1.addPointsFromInputCloud();Eigen::Vector3f p(a1 - range, min(trail->points[i + 8].y, trail->points[i + 12].y), -100000);//min(a2, b22)Eigen::Vector3f q(a1 + range, max(trail->points[i + 8].y, trail->points[i + 12].y) - 0.000001, min(a3, b3));//max(a2, b22) - 0.001octree1.boxSearch(p, q, pointIdx1);cout << "这段种子数:" << pointIdx1.size() << endl;pcl::copyPointCloud(*part, pointIdx1, *partSeed);*seed += *partSeed;/*    cout << "保存2.pcd成功" << endl;pcl::io::savePCDFileASCII("2.pcd", *partSeed);*/// 创建空的tree   设置搜索的方式或者说是结构pcl::search::Search<pcl::PointXYZRGB>::Ptr tree = boost::shared_ptr<pcl::search::Search<pcl::PointXYZRGB> >(new pcl::search::KdTree<pcl::PointXYZRGB>);//求法线//创建一个normal点云pcl::PointCloud <pcl::Normal>::Ptr normals(new pcl::PointCloud <pcl::Normal>);pcl::NormalEstimation<pcl::PointXYZRGB, pcl::Normal> normal_estimator;normal_estimator.setSearchMethod(tree);normal_estimator.setInputCloud(part);normal_estimator.setKSearch(500);normal_estimator.compute(*normals);//创造区域生长分割对象    聚类对象<点,法线>pcl::RegionGrowing<pcl::PointXYZRGB, pcl::Normal> reg; //首先建立reg寄存器(区域曾长的对象)reg.setMinClusterSize(50);  //最小的聚类的点数(小于这参数的平面被忽略不计)reg.setMaxClusterSize(30000000);  //最大的(一般随便设置)reg.setSearchMethod(tree);    //搜索方式(采用的默认是K—d树法)reg.setNumberOfNeighbours(30); //设置搜索的邻域点的个数,周围多少个点决定这是一个平面(决定容错率,设置大时有倾斜也可接受,设置小时检测到的平面会很小)reg.setInputCloud(part);         //输入点//reg.setIndices (indices);reg.setInputNormals(normals);     //输入的法线reg.setSmoothnessThreshold(SmoothnessThreshold / 180.0 * M_PI);//3.0 设置平滑度(设置两个法线在多大夹角内可当做是共面的)reg.setCurvatureThreshold(CurvatureThreshold);std::vector <pcl::PointIndices> clusters;reg.extract(clusters);pcl::PointIndices cluster;reg.getSegmentFromPoint(pointIdx1[0], cluster);cout << "取得的种子是:" << pointIdx1[0] << "\t生长后点数:" << cluster.indices.size() << endl;cout << "种子点" << part->points[pointIdx1[0]].x << "\t" << part->points[pointIdx1[0]].y << "\t" << part->points[pointIdx1[0]].z << "\t" << endl;cout << "-------------------------------------------------------------" << endl;pcl::copyPointCloud(*part, cluster, *tempCloud);*result += *tempCloud;}cout << "生长后的点云保存到result.pcd,0result.pcd" << endl;pcl::io::savePCDFileASCII("0result.pcd", *result);cout << "保存成功" << endl;cout << "切割后的点云保存到seedCloud,seedCloud.pcd" << endl;pcl::io::savePCDFileASCII("0seedCloud.pcd", *seed);cout << "保存成功" << endl;return 0;
}

Project1,添加输入las文件的函数

#include <pcl/visualization/cloud_viewer.h>
#include <iostream>//标准C++库中的输入输出类相关头文件。
#include <pcl/io/io.h>
#include <pcl/io/pcd_io.h>//pcd 读写类相关的头文件。
#include <pcl/io/ply_io.h>
#include <pcl/point_types.h> //PCL中支持的点类型头文件。
#include <pcl/octree/octree.h>
#include<fstream>
#include <string>
#include <vector>
#include <LasOperator.h>
#include <liblas/liblas.hpp>
#include <pcl/filters/passthrough.h>
#include <pcl/segmentation/region_growing.h>
#include <pcl/search/search.h>
#include <pcl/search/kdtree.h>
#include <pcl/features/normal_3d.h>using namespace std;void loadLasFile(string s, pcl::PointCloud<pcl::PointXYZRGB> &cloud);
void loadLasFile(string s, pcl::PointCloud<pcl::PointXYZRGB> &cloud) {/**读取las文件*/std::ifstream ifs(s, std::ios::in | std::ios::binary); // 打开las文件liblas::ReaderFactory f;liblas::Reader reader = f.CreateWithStream(ifs); // 读取las文件unsigned long int nbPoints = reader.GetHeader().GetPointRecordsCount();//获取las数据点的个数cloud.width = nbPoints;  //保证与las数据点的个数一致    cloud.height = 1;cloud.is_dense = false;cloud.points.resize(cloud.width * cloud.height);int i = 0;uint16_t r1, g1, b1;int r2, g2, b2;uint32_t rgb;while (reader.ReadNextPoint()) {// 获取las数据的x,y,z信息cloud.points[i].x = (reader.GetPoint().GetX());cloud.points[i].y = (reader.GetPoint().GetY());cloud.points[i].z = (reader.GetPoint().GetZ());//获取las数据的r,g,b信息r1 = (reader.GetPoint().GetColor().GetRed());g1 = (reader.GetPoint().GetColor().GetGreen());b1 = (reader.GetPoint().GetColor().GetBlue());r2 = ceil(((float)r1 / 65536)*(float)256);g2 = ceil(((float)g1 / 65536)*(float)256);b2 = ceil(((float)b1 / 65536)*(float)256);rgb = ((int)r2) << 16 | ((int)g2) << 8 | ((int)b2);cloud.points[i].rgb = *reinterpret_cast<float*>(&rgb);i++;}
}int main() {/**定义变量*///输入点云,轨迹线,保存种子pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZ>::Ptr trail(new pcl::PointCloud<pcl::PointXYZ>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud2(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr result(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr part(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr partSeed(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr seed(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr colored(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointXYZRGB tempPnt;//变量float x1, y1, x2, y2, a1, a2, a3, b11, b22, b3;//向量1,a,b为轨迹线上2点x1 = y1 = a1 = a2 = a3 = b11 = b22 = b3 = 0;x2 = 0; y2 = 1;float r = 1; //半径2float SmoothnessThreshold =6;//3.0 0.37float CurvatureThreshold = 0.01;    //设置曲率的阈值1.0//读取输入电云cout << "读取点云" << endl;//pcl::io::loadPCDFile("sample100.pcd", *cloud);loadLasFile("sample10.las", *cloud);//读取轨迹线cout << "读取轨迹线" << endl;pcl::io::loadPCDFile("trail.pcd", *trail);cout << "原始点数: " << cloud->width << " \t" <<  "轨迹线点数: " << trail->width  << endl;//cloud构建八叉树cout << "构建八叉树" << endl;float resolution = 128.0f;pcl::octree::OctreePointCloudSearch<pcl::PointXYZRGB> octree(resolution);octree.setInputCloud(cloud);octree.addPointsFromInputCloud();std::vector<int>pointIdxRadiusSearch;std::vector<int>pointIdxRadiusSearch1;//seed.txt保存切割得到的种子索引ofstream ofs;ofs.open("seed.txt");/**开始循环*/for (size_t i = 0; i < trail->points.size() + 500; i += 20) {//cloud1->points.size()        cloud1->points.size()+500   500cout << "-------------------------------------------------------------" << endl;a1 = trail->points[i].x;a2 = trail->points[i].y;//cloud1->points[i+8].ya3 = trail->points[i].z;b11 = trail->points[i + 20].x;b22 = trail->points[i + 20].y;//cloud1->points[i+12].yb3 = trail->points[i + 20].z;x1 = a1 - b11;y1 = a2 - b22;float cosa = (x1*x2 + y1 * y2) / (sqrt(x1*x1 + y1 * y1) + sqrt(x2*x2 + y2 * y2));float sina = sqrt(1 - cosa * cosa);float range = r / sina;//分段Eigen::Vector3f n(-100000, min(a2, b22), -100000);//0xc0c0c0c0  0x3f3f3f3fEigen::Vector3f m(100000, max(a2, b22) - 0.001, min(a3, b3));octree.boxSearch(n, m, pointIdxRadiusSearch);cout << i<<" 这段有点数:" << pointIdxRadiusSearch.size() << "\t";for (size_t j = 0; j < pointIdxRadiusSearch.size(); ++j) {tempPnt.x = cloud->points[pointIdxRadiusSearch[j]].x;tempPnt.y = cloud->points[pointIdxRadiusSearch[j]].y;tempPnt.z = cloud->points[pointIdxRadiusSearch[j]].z;tempPnt.rgb = cloud->points[pointIdxRadiusSearch[j]].rgb;part->push_back(tempPnt);}/*cout << "保存1.pcd成功" << endl;pcl::io::savePCDFileASCII("1.pcd", *part);*///分段切割种子点pcl::octree::OctreePointCloudSearch<pcl::PointXYZRGB> octree1(resolution);octree1.setInputCloud(part);octree1.addPointsFromInputCloud();Eigen::Vector3f p(a1 - range, min(trail->points[i + 8].y, trail->points[i + 12].y), -100000);//min(a2, b22)Eigen::Vector3f q(a1 + range, max(trail->points[i + 8].y, trail->points[i + 12].y)-0.000001, min(a3, b3));//max(a2, b22) - 0.001octree1.boxSearch(p, q, pointIdxRadiusSearch1);cout << "这段种子数:" << pointIdxRadiusSearch1.size() << endl;for (size_t j = 0; j < pointIdxRadiusSearch1.size(); ++j) {tempPnt.x = part->points[pointIdxRadiusSearch1[j]].x;tempPnt.y = part->points[pointIdxRadiusSearch1[j]].y;tempPnt.z = part->points[pointIdxRadiusSearch1[j]].z;tempPnt.rgb = part->points[pointIdxRadiusSearch1[j]].rgb;seed->push_back(tempPnt);}/*    cout << "保存2.pcd成功" << endl;pcl::io::savePCDFileASCII("2.pcd", *partSeed);*/// 创建空的tree   设置搜索的方式或者说是结构pcl::search::Search<pcl::PointXYZRGB>::Ptr tree = boost::shared_ptr<pcl::search::Search<pcl::PointXYZRGB> >(new pcl::search::KdTree<pcl::PointXYZRGB>);//求法线//创建一个normal点云pcl::PointCloud <pcl::Normal>::Ptr normals(new pcl::PointCloud <pcl::Normal>);pcl::NormalEstimation<pcl::PointXYZRGB, pcl::Normal> normal_estimator;normal_estimator.setSearchMethod(tree);normal_estimator.setInputCloud(part);normal_estimator.setKSearch(500);normal_estimator.compute(*normals);//创造区域生长分割对象    聚类对象<点,法线>pcl::RegionGrowing<pcl::PointXYZRGB, pcl::Normal> reg; //首先建立reg寄存器(区域曾长的对象)reg.setMinClusterSize(50);  //最小的聚类的点数(小于这参数的平面被忽略不计)reg.setMaxClusterSize(30000000);  //最大的(一般随便设置)reg.setSearchMethod(tree);    //搜索方式(采用的默认是K—d树法)reg.setNumberOfNeighbours(30); //设置搜索的邻域点的个数,周围多少个点决定这是一个平面(决定容错率,设置大时有倾斜也可接受,设置小时检测到的平面会很小)reg.setInputCloud(part);         //输入点//reg.setIndices (indices);reg.setInputNormals(normals);     //输入的法线reg.setSmoothnessThreshold(SmoothnessThreshold / 180.0 * M_PI);//3.0 设置平滑度(设置两个法线在多大夹角内可当做是共面的)reg.setCurvatureThreshold(CurvatureThreshold);std::vector <pcl::PointIndices> clusters;reg.extract(clusters);pcl::PointIndices cluster;//for (int j = 0;j < pointIdxRadiusSearch1.size();++j) {// reg.getSegmentFromPoint(pointIdxRadiusSearch1[0], cluster);//   for (int j = 0; j < cluster.indices.size(); ++j) {//      tempPnt.x = part->points[cluster.indices[j]].x;//       tempPnt.y = part->points[cluster.indices[j]].y;//       tempPnt.z = part->points[cluster.indices[j]].z;//       tempPnt.rgb = part->points[cluster.indices[j]].rgb;//       cloud3->push_back(tempPnt);//    }//}reg.getSegmentFromPoint(pointIdxRadiusSearch1[0], cluster);cout << "取得的种子是:" << pointIdxRadiusSearch1[0] << "\t生长后点数:" << cluster.indices.size() << endl;cout << "种子点" << part->points[pointIdxRadiusSearch1[0]].x << "\t" << part->points[pointIdxRadiusSearch1[0]].y << "\t" << part->points[pointIdxRadiusSearch1[0]].z << "\t" << endl;cout << "-------------------------------------------------------------" << endl;for (int j = 0; j < cluster.indices.size(); ++j) {tempPnt.x = part->points[cluster.indices[j]].x;tempPnt.y = part->points[cluster.indices[j]].y;tempPnt.z = part->points[cluster.indices[j]].z;tempPnt.rgb = part->points[cluster.indices[j]].rgb;result->push_back(tempPnt);}part->clear();partSeed->clear();}ofs.close();cout << "生长后的点云保存到result.pcd,0result.pcd" << endl;pcl::io::savePCDFileASCII("0result.pcd", *result);cout << "保存成功" << endl;cout << "切割后的点云保存到seedCloud,seedCloud.pcd" << endl;pcl::io::savePCDFileASCII("0seedCloud.pcd", *seed);cout << "保存成功" << endl;return 0;
}

Project1,pcd输入文件,修改点云变量名

#include <pcl/visualization/cloud_viewer.h>
#include <iostream>//标准C++库中的输入输出类相关头文件。
#include <pcl/io/io.h>
#include <pcl/io/pcd_io.h>//pcd 读写类相关的头文件。
#include <pcl/io/ply_io.h>
#include <pcl/point_types.h> //PCL中支持的点类型头文件。
#include <pcl/octree/octree.h>
#include<fstream>
#include <string>
#include <vector>
#include <LasOperator.h>
#include <liblas/liblas.hpp>
#include <pcl/filters/passthrough.h>
#include <pcl/segmentation/region_growing.h>
#include <pcl/search/search.h>
#include <pcl/search/kdtree.h>
#include <pcl/features/normal_3d.h>using namespace std;int main() {/**定义变量*///输入点云,轨迹线,保存种子pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZ>::Ptr trail(new pcl::PointCloud<pcl::PointXYZ>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud2(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr result(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr part(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr partSeed(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr seed(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr colored(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointXYZRGB tempPnt;//变量float x1, y1, x2, y2, a1, a2, a3, b11, b22, b3;//向量1,a,b为轨迹线上2点x1 = y1 = a1 = a2 = a3 = b11 = b22 = b3 = 0;x2 = 0; y2 = 1;float r = 1; //半径2float SmoothnessThreshold =6;//3.0 0.37float CurvatureThreshold = 0.01;    //设置曲率的阈值1.0//读取输入电云cout << "读取点云" << endl;pcl::io::loadPCDFile("o.pcd", *cloud);//读取轨迹线cout << "读取轨迹线" << endl;pcl::io::loadPCDFile("trail.pcd", *trail);cout << "原始点数: " << cloud->width << " \t" <<  "轨迹线点数: " << trail->width  << endl;//cloud构建八叉树cout << "构建八叉树" << endl;float resolution = 128.0f;pcl::octree::OctreePointCloudSearch<pcl::PointXYZRGB> octree(resolution);octree.setInputCloud(cloud);octree.addPointsFromInputCloud();std::vector<int>pointIdxRadiusSearch;std::vector<int>pointIdxRadiusSearch1;//seed.txt保存切割得到的种子索引ofstream ofs;ofs.open("seed.txt");/**开始循环*/for (size_t i = 0; i < trail->points.size() + 500; i += 20) {//cloud1->points.size()        cloud1->points.size()+500   500cout << "-------------------------------------------------------------" << endl;a1 = trail->points[i].x;a2 = trail->points[i].y;//cloud1->points[i+8].ya3 = trail->points[i].z;b11 = trail->points[i + 20].x;b22 = trail->points[i + 20].y;//cloud1->points[i+12].yb3 = trail->points[i + 20].z;x1 = a1 - b11;y1 = a2 - b22;float cosa = (x1*x2 + y1 * y2) / (sqrt(x1*x1 + y1 * y1) + sqrt(x2*x2 + y2 * y2));float sina = sqrt(1 - cosa * cosa);float range = r / sina;//分段Eigen::Vector3f n(-100000, min(a2, b22), -100000);//0xc0c0c0c0  0x3f3f3f3fEigen::Vector3f m(100000, max(a2, b22) - 0.001, min(a3, b3));octree.boxSearch(n, m, pointIdxRadiusSearch);cout << i<<" 这段有点数:" << pointIdxRadiusSearch.size() << "\t";for (size_t j = 0; j < pointIdxRadiusSearch.size(); ++j) {tempPnt.x = cloud->points[pointIdxRadiusSearch[j]].x;tempPnt.y = cloud->points[pointIdxRadiusSearch[j]].y;tempPnt.z = cloud->points[pointIdxRadiusSearch[j]].z;tempPnt.rgb = cloud->points[pointIdxRadiusSearch[j]].rgb;part->push_back(tempPnt);}/*cout << "保存1.pcd成功" << endl;pcl::io::savePCDFileASCII("1.pcd", *part);*///分段切割种子点pcl::octree::OctreePointCloudSearch<pcl::PointXYZRGB> octree1(resolution);octree1.setInputCloud(part);octree1.addPointsFromInputCloud();Eigen::Vector3f p(a1 - range, min(trail->points[i + 8].y, trail->points[i + 12].y), -100000);//min(a2, b22)Eigen::Vector3f q(a1 + range, max(trail->points[i + 8].y, trail->points[i + 12].y)-0.000001, min(a3, b3));//max(a2, b22) - 0.001octree1.boxSearch(p, q, pointIdxRadiusSearch1);cout << "这段种子数:" << pointIdxRadiusSearch1.size() << endl;for (size_t j = 0; j < pointIdxRadiusSearch1.size(); ++j) {tempPnt.x = part->points[pointIdxRadiusSearch1[j]].x;tempPnt.y = part->points[pointIdxRadiusSearch1[j]].y;tempPnt.z = part->points[pointIdxRadiusSearch1[j]].z;tempPnt.rgb = part->points[pointIdxRadiusSearch1[j]].rgb;seed->push_back(tempPnt);}/*    cout << "保存2.pcd成功" << endl;pcl::io::savePCDFileASCII("2.pcd", *partSeed);*/// 创建空的tree   设置搜索的方式或者说是结构pcl::search::Search<pcl::PointXYZRGB>::Ptr tree = boost::shared_ptr<pcl::search::Search<pcl::PointXYZRGB> >(new pcl::search::KdTree<pcl::PointXYZRGB>);//求法线//创建一个normal点云pcl::PointCloud <pcl::Normal>::Ptr normals(new pcl::PointCloud <pcl::Normal>);pcl::NormalEstimation<pcl::PointXYZRGB, pcl::Normal> normal_estimator;normal_estimator.setSearchMethod(tree);normal_estimator.setInputCloud(part);normal_estimator.setKSearch(500);normal_estimator.compute(*normals);//创造区域生长分割对象    聚类对象<点,法线>pcl::RegionGrowing<pcl::PointXYZRGB, pcl::Normal> reg; //首先建立reg寄存器(区域曾长的对象)reg.setMinClusterSize(50);  //最小的聚类的点数(小于这参数的平面被忽略不计)reg.setMaxClusterSize(30000000);  //最大的(一般随便设置)reg.setSearchMethod(tree);    //搜索方式(采用的默认是K—d树法)reg.setNumberOfNeighbours(30); //设置搜索的邻域点的个数,周围多少个点决定这是一个平面(决定容错率,设置大时有倾斜也可接受,设置小时检测到的平面会很小)reg.setInputCloud(part);         //输入点//reg.setIndices (indices);reg.setInputNormals(normals);     //输入的法线reg.setSmoothnessThreshold(SmoothnessThreshold / 180.0 * M_PI);//3.0 设置平滑度(设置两个法线在多大夹角内可当做是共面的)reg.setCurvatureThreshold(CurvatureThreshold);std::vector <pcl::PointIndices> clusters;reg.extract(clusters);pcl::PointIndices cluster;//for (int j = 0;j < pointIdxRadiusSearch1.size();++j) {// reg.getSegmentFromPoint(pointIdxRadiusSearch1[0], cluster);//   for (int j = 0; j < cluster.indices.size(); ++j) {//      tempPnt.x = part->points[cluster.indices[j]].x;//       tempPnt.y = part->points[cluster.indices[j]].y;//       tempPnt.z = part->points[cluster.indices[j]].z;//       tempPnt.rgb = part->points[cluster.indices[j]].rgb;//       cloud3->push_back(tempPnt);//    }//}reg.getSegmentFromPoint(pointIdxRadiusSearch1[0], cluster);cout << "取得的种子是:" << pointIdxRadiusSearch1[0] << "\t生长后点数:" << cluster.indices.size() << endl;cout << "种子点" << part->points[pointIdxRadiusSearch1[0]].x << "\t" << part->points[pointIdxRadiusSearch1[0]].y << "\t" << part->points[pointIdxRadiusSearch1[0]].z << "\t" << endl;cout << "-------------------------------------------------------------" << endl;for (int j = 0; j < cluster.indices.size(); ++j) {tempPnt.x = part->points[cluster.indices[j]].x;tempPnt.y = part->points[cluster.indices[j]].y;tempPnt.z = part->points[cluster.indices[j]].z;tempPnt.rgb = part->points[cluster.indices[j]].rgb;result->push_back(tempPnt);}part->clear();partSeed->clear();}ofs.close();cout << "生长后的点云保存到cloud3,0result.pcd" << endl;pcl::io::savePCDFileASCII("0result.pcd", *result);cout << "保存成功" << endl;cout << "切割后的点云保存到seedCloud,seedCloud.pcd" << endl;pcl::io::savePCDFileASCII("0seedCloud.pcd", *seed);cout << "保存成功" << endl;return 0;
}

Project1,分段切割、区域生长,sample100测试得到的结果没有边缘,但是不连续

#include <pcl/visualization/cloud_viewer.h>
#include <iostream>//标准C++库中的输入输出类相关头文件。
#include <pcl/io/io.h>
#include <pcl/io/pcd_io.h>//pcd 读写类相关的头文件。
#include <pcl/io/ply_io.h>
#include <pcl/point_types.h> //PCL中支持的点类型头文件。
#include <pcl/octree/octree.h>
#include<fstream>
#include <string>
#include <vector>
#include <LasOperator.h>
#include <liblas/liblas.hpp>
#include <pcl/filters/passthrough.h>
#include <pcl/segmentation/region_growing.h>
#include <pcl/search/search.h>
#include <pcl/search/kdtree.h>
#include <pcl/features/normal_3d.h>using namespace std;int main() {/**定义变量*///输入点云,轨迹线,保存种子pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZ>::Ptr cloud1(new pcl::PointCloud<pcl::PointXYZ>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud2(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud3(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr part(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr partSeed(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr seedCloud(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointCloud<pcl::PointXYZRGB>::Ptr colored(new pcl::PointCloud<pcl::PointXYZRGB>);pcl::PointXYZRGB tempPnt;//变量float x1, y1, x2, y2, a1, a2, a3, b11, b22, b3;//向量1,a,b为轨迹线上2点x1 = y1 = a1 = a2 = a3 = b11 = b22 = b3 = 0;x2 = 0; y2 = 1;float r = 1;   //半径2float SmoothnessThreshold =6;//3.0 0.37float CurvatureThreshold = 0.01;    //设置曲率的阈值1.0/**读取las文件,打开点云,初始化octree*/std::ifstream ifs("sample10.las", std::ios::in | std::ios::binary); // 打开las文件liblas::ReaderFactory f;liblas::Reader reader = f.CreateWithStream(ifs); // 读取las文件unsigned long int nbPoints = reader.GetHeader().GetPointRecordsCount();//获取las数据点的个数cloud->width = nbPoints;    //保证与las数据点的个数一致    cloud->height = 1;cloud->is_dense = false;cloud->points.resize(cloud->width * cloud->height);part->width = 0;part->height = 1;part->is_dense = false;part->points.resize(part->width * part->height);partSeed->width = 0;partSeed->height = 1;partSeed->is_dense = false;partSeed->points.resize(partSeed->width * partSeed->height);int i = 0;uint16_t r1, g1, b1;int r2, g2, b2;uint32_t rgb;while (reader.ReadNextPoint()) {// 获取las数据的x,y,z信息cloud->points[i].x = (reader.GetPoint().GetX());cloud->points[i].y = (reader.GetPoint().GetY());cloud->points[i].z = (reader.GetPoint().GetZ());//获取las数据的r,g,b信息r1 = (reader.GetPoint().GetColor().GetRed());g1 = (reader.GetPoint().GetColor().GetGreen());b1 = (reader.GetPoint().GetColor().GetBlue());r2 = ceil(((float)r1 / 65536)*(float)256);g2 = ceil(((float)g1 / 65536)*(float)256);b2 = ceil(((float)b1 / 65536)*(float)256);rgb = ((int)r2) << 16 | ((int)g2) << 8 | ((int)b2);cloud->points[i].rgb = *reinterpret_cast<float*>(&rgb);i++;}float resolution = 128.0f;pcl::octree::OctreePointCloudSearch<pcl::PointXYZRGB> octree(resolution);octree.setInputCloud(cloud);octree.addPointsFromInputCloud();std::vector<int>pointIdxRadiusSearch;std::vector<int>pointIdxRadiusSearch1;cout << "原始点云: " << cloud->width << " \t" << cloud->points.size() << endl;//读取轨迹线pcl::io::loadPCDFile("trail.pcd", *cloud1);cout << "轨迹线: " << cloud1->width << " \t" << cloud1->points.size() << endl;//seed.txt保存切割得到的种子索引ofstream ofs;ofs.open("seed.txt");//cluster保存区域生长得到的分段//pcl::PointIndices tempCluster;/**开始循环*/for (size_t i = 0; i < cloud1->points.size() + 500; i += 20) {//cloud1->points.size()     cloud1->points.size()+500   500//a1 = cloud1->points[i].x;a2 = cloud1->points[i].y;//cloud1->points[i+8].ya3 = cloud1->points[i].z;b11 = cloud1->points[i + 20].x;b22 = cloud1->points[i + 20].y;//cloud1->points[i+12].yb3 = cloud1->points[i + 20].z;x1 = a1 - b11;y1 = a2 - b22;float cosa = (x1*x2 + y1 * y2) / (sqrt(x1*x1 + y1 * y1) + sqrt(x2*x2 + y2 * y2));float sina = sqrt(1 - cosa * cosa);float range = r / sina;//分段Eigen::Vector3f n(-100000, min(a2, b22), -100000);//0xc0c0c0c0    0x3f3f3f3fEigen::Vector3f m(100000, max(a2, b22) - 0.001, min(a3, b3));octree.boxSearch(n, m, pointIdxRadiusSearch);cout << "这段有点数:" << pointIdxRadiusSearch.size() << endl;for (size_t j = 0; j < pointIdxRadiusSearch.size(); ++j) {tempPnt.x = cloud->points[pointIdxRadiusSearch[j]].x;tempPnt.y = cloud->points[pointIdxRadiusSearch[j]].y;tempPnt.z = cloud->points[pointIdxRadiusSearch[j]].z;tempPnt.rgb = cloud->points[pointIdxRadiusSearch[j]].rgb;part->push_back(tempPnt);}/*cout << "保存1.pcd成功" << endl;pcl::io::savePCDFileASCII("1.pcd", *part);*///切割种子点pcl::octree::OctreePointCloudSearch<pcl::PointXYZRGB> octree1(resolution);octree1.setInputCloud(part);octree1.addPointsFromInputCloud();Eigen::Vector3f p(a1 - range, min(cloud1->points[i + 8].y, cloud1->points[i + 12].y), -100000);//min(a2, b22)Eigen::Vector3f q(a1 + range, max(cloud1->points[i + 8].y, cloud1->points[i + 12].y)-0.000001, min(a3, b3));//max(a2, b22) - 0.001octree1.boxSearch(p, q, pointIdxRadiusSearch1);cout << i<<"\t"<<"这段种子数:" << pointIdxRadiusSearch1.size() << endl;for (size_t j = 0; j < pointIdxRadiusSearch1.size(); ++j) {tempPnt.x = part->points[pointIdxRadiusSearch1[j]].x;tempPnt.y = part->points[pointIdxRadiusSearch1[j]].y;tempPnt.z = part->points[pointIdxRadiusSearch1[j]].z;tempPnt.rgb = part->points[pointIdxRadiusSearch1[j]].rgb;seedCloud->push_back(tempPnt);}//cout << "能到这里吗" << endl;/*  cout << "保存2.pcd成功" << endl;pcl::io::savePCDFileASCII("2.pcd", *partSeed);*/// 创建空的tree   设置搜索的方式或者说是结构pcl::search::Search<pcl::PointXYZRGB>::Ptr tree = boost::shared_ptr<pcl::search::Search<pcl::PointXYZRGB> >(new pcl::search::KdTree<pcl::PointXYZRGB>);//求法线//创建一个normal点云pcl::PointCloud <pcl::Normal>::Ptr normals(new pcl::PointCloud <pcl::Normal>);pcl::NormalEstimation<pcl::PointXYZRGB, pcl::Normal> normal_estimator;normal_estimator.setSearchMethod(tree);normal_estimator.setInputCloud(part);normal_estimator.setKSearch(500);normal_estimator.compute(*normals);//创造区域生长分割对象    聚类对象<点,法线>pcl::RegionGrowing<pcl::PointXYZRGB, pcl::Normal> reg; //首先建立reg寄存器(区域曾长的对象)reg.setMinClusterSize(50);  //最小的聚类的点数(小于这参数的平面被忽略不计)reg.setMaxClusterSize(30000000);  //最大的(一般随便设置)reg.setSearchMethod(tree);    //搜索方式(采用的默认是K—d树法)reg.setNumberOfNeighbours(30); //设置搜索的邻域点的个数,周围多少个点决定这是一个平面(决定容错率,设置大时有倾斜也可接受,设置小时检测到的平面会很小)reg.setInputCloud(part);         //输入点//reg.setIndices (indices);reg.setInputNormals(normals);     //输入的法线reg.setSmoothnessThreshold(SmoothnessThreshold / 180.0 * M_PI);//3.0 设置平滑度(设置两个法线在多大夹角内可当做是共面的)reg.setCurvatureThreshold(CurvatureThreshold);std::vector <pcl::PointIndices> clusters;reg.extract(clusters);pcl::PointIndices cluster;for (int j = 0;j < pointIdxRadiusSearch1.size();++j) {reg.getSegmentFromPoint(pointIdxRadiusSearch1[0], cluster);for (int j = 0; j < cluster.indices.size(); ++j) {tempPnt.x = part->points[cluster.indices[j]].x;tempPnt.y = part->points[cluster.indices[j]].y;tempPnt.z = part->points[cluster.indices[j]].z;tempPnt.rgb = part->points[cluster.indices[j]].rgb;cloud3->push_back(tempPnt);}}/*reg.getSegmentFromPoint(pointIdxRadiusSearch1[0], cluster);cout << "取得的种子是:" << pointIdxRadiusSearch1[0] << "\t生长后点数:" << cluster.indices.size() << endl;cout << "-------------------------------------------------------------" << endl;cout << "种子点" << part->points[pointIdxRadiusSearch1[0]].x << "\t" << part->points[pointIdxRadiusSearch1[0]].y << "\t" << part->points[pointIdxRadiusSearch1[0]].z << "\t" << endl;*/for (int j = 0; j < cluster.indices.size(); ++j) {tempPnt.x = part->points[cluster.indices[j]].x;tempPnt.y = part->points[cluster.indices[j]].y;tempPnt.z = part->points[cluster.indices[j]].z;tempPnt.rgb = part->points[cluster.indices[j]].rgb;cloud3->push_back(tempPnt);}//cluster.indices.clear();pointIdxRadiusSearch.clear();pointIdxRadiusSearch1.clear();part->clear();partSeed->clear();}ofs.close();cout << "生长后的点云保存到cloud3,regionGrow.pcd" << endl;//cloud3->width = cluster.indices.size();  //保证与las数据点的个数一致    cloud3->height = 1;cloud3->is_dense = false;//cloud3->points.resize(cloud3->width * cloud3->height);pcl::io::savePCDFileASCII("0regionGrow.pcd", *cloud3);cout << "保存成功" << endl;cout << "切割后的点云保存到seedCloud,seedCloud.pcd" << endl;//cloud3->width = cluster.indices.size(); //保证与las数据点的个数一致    seedCloud->height = 1;seedCloud->is_dense = false;//cloud3->points.resize(cloud3->width * cloud3->height);pcl::io::savePCDFileASCII("0seedCloud.pcd", *seedCloud);cout << "保存成功" << endl;return 0;
}

Project1,分段切割、区域生长,sample100测试得到的结果没有边缘,但是不连续相关推荐

  1. Project2 分段切割路面,只取一个种子点

    分段切割路面,只取一个种子点 #include <pcl/visualization/cloud_viewer.h> #include <iostream>//标准C++库中的 ...

  2. 【涡扇发动机RUL专题】:分段退化标签,测试集可视化、评价指标

    涡扇发动机RUL预测 常用的数据处理技术 分段线性退化标签处理 评价指标 单台发动机可视化 单独可视化的效果 查看任意一台发动机的RUL预测情况 总结 常用的数据处理技术 一直以为涡扇发动机的RUL不 ...

  3. 渗透测试工作流程渗透测试类型法律边界

    渗透测试工作流程渗透测试类型法律边界 渗透测试工作流程 渗透测试与其它评估方法不同.通常的评估方法是根据已知信息资源或其它被评估对象,去发现所有相关的安全问题.渗透测试是根据已知可利用的安全漏洞,去发 ...

  4. centos7 tomcat_centos7中利用logrotate工具切割日志,以tomcat日志为例

    程序在运行的时候为了了解运行状态,会输出日志文件,时间久了日志文件会变得非常大. 1. logrotate简介: 强大的系统软件,对日志文件有着一套完整的操作模式. 例如:转储 把旧的日志文件删除,并 ...

  5. 微服务精华问答 | 微服务如何测试?

    戳蓝字"CSDN云计算"关注我们哦! 微服务(Microservice Architecture)是近几年流行的一种架构思想,关于它的概念很难一言以蔽之.今天,就让我们来看看关于微 ...

  6. 基于改进区域生长算法的图像分割方法及实现

    一.题目与要求 1.1课程设计题目 采用灰度图像(该图像由高分二号卫星拍摄,是武汉市江夏区矿区的部分灰度图像)分别实现几种图像分割方法: (1) 经典区域生长方法: (2) 改进的区域生长方法: (3 ...

  7. Android 8.0 VTS 测试 FAIL 项解决记录

    本文是转自https://zhuanlan.zhihu.com/p/28426650 注意:本文基于 Android 8.0 进行分析. 1. 前言 这篇文章所记录的是我自己在 Amlogic 平台上 ...

  8. 这些单晶XRD测试问题你了解吗?(二)

    1.怎么看独立可观测点和衍射点分别是多少? 答:可以在后缀是.abs文件中查看. 2.没有吸收校正文件,对后期发文章有影响吗? 答:这个不是必要提交文件,发文章主要提交cif, checkcif文件. ...

  9. 可靠性测试设备技术含量_智能降噪耳机可靠性测试标准

    序号 测试项目 测试要求 测试说明 测试装置示意图 适用范围 样品数量 测试评价 完成时间 测试结果 问题描述 0 测试之前的外观和功能检查 1. 检查测试样品及连接线是否为最新版本:样 品外观是否良 ...

最新文章

  1. 设置tomcat服务为80端口,tomcat虚拟主机,tomcat日志
  2. 为什么先交钱后用电_适合痘痘痘印的好的护肤品,为什么要先清洁后祛痘!_新闻中心...
  3. 我是如何成功准备VUE项目之前的开发环境?
  4. android代码混淆作用,Android分享:代码混淆那些事
  5. redis复制key的数据_Redis常见面试题
  6. Android对点击事件的处理
  7. JS中的数组排序函数sort()
  8. 从零开始的硬改路由器记录
  9. Floyd-Warshall算法过程中矩阵计算方法—十字交叉法(转)
  10. PhantomJS的安装
  11. Python动态图见得多了?Excel:亦可赛艇!我可是身经百战了
  12. python画国际象棋_python使用turtle绘制国际象棋棋盘
  13. 【华为OD机试/笔试真题 python】出错的或电路
  14. 使用telnet登陆smtp服务发邮件(带身份验证)
  15. AppList数据处理
  16. 迪克莫利-PLC之父
  17. iOS跑步软件开发-从无到有
  18. 如果更有效预防应力作用?PCB设计如何考虑应力作用? 应力对元器件失效问题的讨论
  19. Unity—Lerp插值函数
  20. [转贴]LINUX新手入门及安装配置FAQv

热门文章

  1. java mysql 快速插入1000w条数据_教你88秒插入1000万条数据到mysql数据库表
  2. python 时间戳转iso 8601_ISO8601时间字符串到时间戳处理
  3. 诺基亚n1系统更新显示无网络_诺基亚要回归手机行业?再次更新塞班系统,激起市场上无数的情怀...
  4. 很简单的网络渗透过程
  5. Unity场景美术资源优化
  6. 《人性的弱点》阅读摘录-2
  7. Python爬取、分析全球最美Top100女神榜单的数据
  8. Python网络爬虫及自动化——核酸查询并截图
  9. 我眼中的林徽因,梁思成
  10. 推荐系统应用研究:音乐电台