evaluation_fpfh_svm_trainer.cpp
Go to the documentation of this file.
00001 
00063 #include <boost/program_options.hpp>
00064 #include <iostream>
00065 
00066 #include <pcl/point_types.h>
00067 #include <pcl/io/pcd_io.h>
00068 #include <pcl/common/file_io.h>
00069 
00070 #include <opencv2/ml/ml.hpp>
00071 #include <sensor_msgs/PointCloud2.h>
00072 
00073 #include <cob_3d_mapping_common/label_defines.h>
00074 
00075 using namespace std;
00076 using namespace pcl;
00077 
00078 string file_plane;
00079 string file_edge;
00080 string file_corner;
00081 string file_sphere;
00082 string file_cylinder;
00083 string file_folder = "";
00084 
00085 double svm_gamma;
00086 double svm_c;
00087 int svm_k;
00088 
00089 int svm_samples;
00090 
00091 void readOptions(int argc, char* argv[])
00092 {
00093   using namespace boost::program_options;
00094   
00095   options_description cmd_line("Options");
00096   cmd_line.add_options()
00097     ("help", "produce help messsage")
00098     ("svm_gamma,g", value<double>(&svm_gamma)->default_value(1.0), 
00099      "Training parameter gamma")
00100     ("svm_c,c", value<double>(&svm_c)->default_value(1.0),
00101      "Training parameter c")
00102     ("svm_k,k", value<int>(&svm_k)->default_value(0),
00103      "Set k_fold != 0 to use train_auto")
00104     ("folder,f", value<string>(&file_folder),
00105      "path to folder containing a pcd file for each class. "
00106      "If this is defined all seperatly defined files will be ignored.")
00107     ("svm_max_samples,s", value<int>(&svm_samples)->default_value(0),
00108      "maximal number of samples per class. (0 for all)")
00109     ;
00110   variables_map vm;
00111   store(command_line_parser(argc, argv).options(cmd_line).run(), vm);
00112   notify(vm);
00113 
00114   if (vm.count("help"))
00115   {
00116     cout << "Reads files containing FPFH features and creates a SVM model" << endl;
00117     cout << "The following files from the defined folder containing the strings are used:" << endl;
00118     cout << "\t  \"fpfh_plane.pcd\"" << endl;
00119     cout << "\t  \"fpfh_edge.pcd\"" << endl;
00120     cout << "\t  \"fpfh_cor.pcd\"" << endl;
00121     cout << "\t  \"fpfh_sph.pcd\"" << endl;
00122     cout << "\t  \"fpfh_cyl.pcd\"" << endl;
00123     cout << cmd_line << endl;
00124     exit(0);
00125   }
00126 
00127   if (vm.count("folder"))
00128   {
00129     vector<string> files;
00130     //    PCDReader r;
00131     sensor_msgs::PointCloud2 c;
00132     getAllPcdFilesInDirectory(file_folder, files);
00133     for (unsigned int i = 0; i < files.size(); i++)
00134     {
00135       files[i] = file_folder + files[i];
00136       // if(!r.read(files[i], c))
00137       //        continue;
00138       // if(getFieldIndex(c, "histogram") == -1) 
00139       //        continue;
00140       if(string::npos != files[i].rfind("fpfh_plane"))
00141         file_plane = files[i];
00142       else if (string::npos != files[i].rfind("fpfh_edge"))
00143         file_edge = files[i];
00144       else if (string::npos != files[i].rfind("fpfh_cor"))
00145         file_corner = files[i];
00146       else if (string::npos != files[i].rfind("fpfh_sph"))
00147         file_sphere = files[i];
00148       else if (string::npos != files[i].rfind("fpfh_cyl"))
00149         file_cylinder = files[i];
00150     }
00151   }
00152 }
00153 
00154 int main(int argc, char** argv)
00155 {
00156   readOptions(argc, argv);
00157 
00158   PointCloud<FPFHSignature33>::Ptr p_plane (new PointCloud<FPFHSignature33>);
00159   PointCloud<FPFHSignature33>::Ptr p_edge (new PointCloud<FPFHSignature33>);
00160   PointCloud<FPFHSignature33>::Ptr p_corner (new PointCloud<FPFHSignature33>);
00161   PointCloud<FPFHSignature33>::Ptr p_cylinder (new PointCloud<FPFHSignature33>);
00162   PointCloud<FPFHSignature33>::Ptr p_sphere (new PointCloud<FPFHSignature33>);
00163 
00164   PCDReader reader;
00165   cout << "Read "<< file_plane << " for plane." << endl;
00166   reader.read(file_plane, *p_plane);
00167   cout << "Read "<< file_edge << " for edge." << endl;
00168   reader.read(file_edge, *p_edge);
00169   cout << "Read "<< file_corner << " for corner." << endl;
00170   reader.read(file_corner, *p_corner);
00171   cout << "Read "<< file_sphere << " for sph." << endl;
00172   reader.read(file_sphere, *p_sphere);
00173   cout << "Read "<< file_cylinder << " for cyl." << endl;
00174   reader.read(file_cylinder, *p_cylinder);
00175 
00176   int plane_samples, edge_samples, corner_samples, sphere_samples, cylinder_samples, sample_count;
00177 
00178   if (svm_samples == 0)
00179   {
00180     plane_samples = p_plane->height * p_plane->width;
00181     edge_samples = p_edge->height * p_edge->width;
00182     sphere_samples =  p_sphere->height * p_sphere->width;
00183     cylinder_samples = p_cylinder->height * p_cylinder->width;
00184     corner_samples = p_corner->height * p_corner->width;
00185   }
00186   else
00187   {
00188     plane_samples = edge_samples = corner_samples = sphere_samples = cylinder_samples = svm_samples;
00189   }
00190   sample_count = plane_samples + edge_samples + corner_samples + sphere_samples + cylinder_samples;
00191   cout << "Found " << sample_count << " samples." << endl;
00192   cv::Mat train_data(sample_count, 33, CV_32FC1);
00193   cv::Mat train_data_classes(sample_count, 1, CV_32FC1);
00194   
00195   // Read FPFHs for Plane Categorie
00196   float* row;
00197   int i_end = 0;
00198   for (int i = 0; i < plane_samples; i ++)
00199   {
00200     train_data_classes.at<float>(i + i_end) = SVM_PLANE;
00201     row = train_data.ptr<float>(i + i_end);
00202     for(int j = 0; j < 33; j++)
00203     {
00204       row[j] = p_plane->points[i].histogram[j];
00205     }
00206   }
00207 
00208   // Read FPFHs for Edge Categorie
00209   i_end += plane_samples;
00210   for (int i = 0; i < edge_samples; i ++)
00211   {
00212     train_data_classes.at<float>(i + i_end) = SVM_EDGE;
00213     row = train_data.ptr<float>(i + i_end);
00214     for(int j = 0; j < 33; j++)
00215     {
00216       row[j] = p_edge->points[i].histogram[j];
00217     }
00218   }
00219 
00220   i_end += edge_samples;
00221   for (int i = 0; i < corner_samples; i ++)
00222   {
00223     train_data_classes.at<float>(i + i_end) = SVM_COR;
00224     row = train_data.ptr<float>(i + i_end);
00225     for(int j = 0; j < 33; j++)
00226     {
00227       row[j] = p_corner->points[i].histogram[j];
00228     }
00229   }
00230 
00231   // Read FPFHs for Sphere Categorie
00232   i_end += corner_samples;
00233   for (int i = 0; i < sphere_samples; i ++)
00234   {
00235     train_data_classes.at<float>(i + i_end) = SVM_SPH;
00236     row = train_data.ptr<float>(i + i_end);
00237     for(int j = 0; j < 33; j++)
00238     {
00239       row[j] = p_sphere->points[i].histogram[j];
00240     }
00241   }
00242 
00243   // Read FPFHs for Cylinder Categorie
00244   i_end += sphere_samples;
00245   for (int i = 0; i < cylinder_samples; i ++)
00246   {
00247     train_data_classes.at<float>(i + i_end) = SVM_CYL;
00248     row = train_data.ptr<float>(i + i_end);
00249     for(int j = 0; j < 33; j++)
00250     {
00251       row[j] = p_cylinder->points[i].histogram[j];
00252     }
00253   }
00254 
00255   cout << "Begin training..." << endl;
00256   CvSVM svm;
00257   CvSVMParams params;
00258   params.svm_type = CvSVM::C_SVC;//NU_SVC;//C_SVC;
00259   params.kernel_type = CvSVM::RBF;
00260   params.nu = 0.5;
00261   params.C = svm_c;
00262   params.gamma = svm_gamma;
00263   // Define iteration termination criteria:
00264   params.term_crit.type = CV_TERMCRIT_ITER | CV_TERMCRIT_EPS;
00265   params.term_crit.max_iter = 1000;
00266   params.term_crit.epsilon = 0.00001;
00267   cout << "Starting training process with " << sample_count << " samples." << endl;
00268   if(svm_k == 0) 
00269     svm.train(train_data, train_data_classes, cv::Mat(), cv::Mat(), params);
00270   else 
00271     svm.train_auto(train_data, train_data_classes, cv::Mat(), cv::Mat(), params, svm_k);
00272   string file_xml = file_folder + "SVM_fpfh_rng_g_c.xml";
00273   svm.save(file_xml.c_str());
00274   //cout << "C: " << params.C << " - Gamma: " << svm_gamma << " / " << params.gamma << endl;
00275   cout << "Training process completed." << endl;
00276 }


cob_3d_evaluation_features
Author(s): Georg Arbeiter
autogenerated on Wed Aug 26 2015 11:04:38