2016-08-08 98 views

回答

0
I did this job. 

#include <CGAL/Exact_predicates_inexact_constructions_kernel.h> 
#include <CGAL/Delaunay_triangulation_3.h> 
#include <CGAL/Triangulation_hierarchy_3.h> 
#include <CGAL/Alpha_shape_3.h> 
#include <CGAL/IO/io.h> 
#include <iostream> 
#include <sstream> 
#include <string> 
#include <fstream> 
#include <CGAL/IO/Writer_OFF.h> 
#include <CGAL/Simple_cartesian.h> 

using namespace std; 


typedef CGAL::Exact_predicates_inexact_constructions_kernel K; 


typedef CGAL::Alpha_shape_vertex_base_3<K>     Vb; 
typedef CGAL::Triangulation_hierarchy_vertex_base_3<Vb>  Vbh; 
typedef CGAL::Alpha_shape_cell_base_3<K>     Fb; 
typedef CGAL::Triangulation_data_structure_3<Vbh, Fb>  Tds; 
typedef CGAL::Delaunay_triangulation_3<K, Tds>    Delaunay; 
typedef CGAL::Triangulation_hierarchy_3<Delaunay>   Delaunay_hierarchy; 
typedef CGAL::Alpha_shape_3<Delaunay_hierarchy>    Alpha_shape_3; 

typedef Alpha_shape_3::Facet        Facet; 
typedef Alpha_shape_3::Edge         Edges; 
typedef Alpha_shape_3::Vertex        Vertex; 

typedef Alpha_shape_3::Vertex_handle      Vertex_handle; 


typedef Alpha_shape_3::Alpha_iterator      Alpha_iterator; 
typedef Alpha_shape_3::NT         NT; 
typedef Alpha_shape_3::Vertex_iterator      Vertex_iterator;     

typedef CGAL::Simple_cartesian<double>      Kernel; 
typedef K::Point_3           Point_3; 


int main(int argc, const char* const argv[]) 
{ 
    if (argc != 3) 
    { 
     std::cerr << "\n There have to be three parameters (name of program, file with coordinates, coefficient)" << std::endl; 
     exit(1); 
    } 
    int mode = static_cast<int>(atoi(argv[1])); 
    std::fstream is(argv[1], std::ios::in); 
    if (!is) 
    { 
     std::cerr << "\n Could not open file " << argv[1] << " for reading, exiting \n"; 
     exit(1); 
    } 
    double coefficient = atof(argv[2]); 


    std::vector<std::vector<Point_3>> points; 
    std::vector<Point_3> coord; 
    char szTempString[1024]; 
    std::string str = "----------End of agglomerate----------"; 
    double dPosX, dPosY, dPosZ; 
    while (is.getline(szTempString, 1024)) 
    { 
     if (szTempString == str) 
     { 
      points.push_back(coord); 
      coord.clear(); 
     } 
     else 
     { 
      sscanf_s(szTempString, "%lf %lf %lf", &dPosX, &dPosY, &dPosZ); 
      coord.push_back(Point_3(dPosX, dPosY, dPosZ)); 
     } 
    } 
    is.close(); 

    for (size_t i = 0; i < points.size(); i++) 
    { 
     Alpha_shape_3 as(points[i].begin(), points[i].end(), 0.001, Alpha_shape_3::GENERAL); 
     Alpha_iterator opt = as.find_optimal_alpha(1); 
     std::cout << "Optimal alpha value to get one connected component is " << std::fixed << std::setprecision(12) << *opt * coefficient << std::endl; 
     as.set_alpha(*opt * coefficient); 
     assert(as.number_of_solid_components() == 1); 

     // collect all regular facets 
     std::vector<Facet> Facets; 
     as.get_alpha_shape_facets(std::back_inserter(Facets), Alpha_shape_3::REGULAR); 

     std::stringstream pts; 
     std::stringstream ind; 

     for (size_t i = 0; i < Facets.size(); i++) 
     { 
      Facet f = Facets[i]; 
      //To have a consistent orientation of the facet, always consider an exterior cell 
      if (as.classify(Facets[i].first) != Alpha_shape_3::EXTERIOR) 
      { 
       Facets[i] = as.mirror_facet(Facets[i]); 
      } 

      CGAL_assertion(as.classify(Facets[i].first) == Alpha_shape_3::EXTERIOR); 

      int indices[3] = { (Facets[i].second + 1) % 4, (Facets[i].second + 2) % 4, (Facets[i].second + 3) % 4 }; 

      /// according to the encoding of vertex indices, this is needed to get a consistent orientation 

      if (Facets[i].second % 2 == 0) 
      { 
       std::swap(indices[0], indices[1]); 
      } 
      pts << Facets[i].first->vertex(indices[0])->point() << "\n" << 
        Facets[i].first->vertex(indices[1])->point() << "\n" << 
        Facets[i].first->vertex(indices[2])->point() << "\n"; 

      ind << "3 " << 3 * i << " " << 3 * i + 1 << " " << 3 * i + 2 << "\n"; 

     } 
      std::ofstream off_file; 
      std::stringstream ss; 
      ss << "agglomerate[" << i << "].off"; 
      off_file.open(ss.str(), std::ios::out); 

      off_file << "OFF " << "\n" << 3 * Facets.size() << " " << Facets.size() << " 0\n"; 
      off_file << pts.str(); 
      off_file << ind.str(); 

    } 
    return 0; 
}