#include <iostream>
#include <string>
#include <fstream>
#include <list>
#include <cassert>
template<class Info_item> struct Info_set_merge_info;
template<class Info_item_t>
class Info_set
{
public:
typedef Info_item_t Info_item;
private:
friend struct Info_set_merge_info<Info_item>;
typedef std::list<Info_item> Info_list;
public:
typedef typename Info_list::const_iterator Info_item_iterator;
typedef typename Info_list::size_type size_type;
Info_set() {}
Info_set(Info_item info) {
info_list_.push_back(info);
}
template<typename InputIterator>
: info_list_(first, beyond) {}
size_type size() const { return info_list_.size(); }
bool is_empty() const { return info_list_.empty(); }
Info_item_iterator info_items_begin() const {
return info_list_.begin();
}
Info_item_iterator info_items_end() const {
return info_list_.end();
}
private:
Info_set(Info_list info_list) : info_list_(info_list) {}
const Info_list& info_list() const { return info_list_; }
private:
Info_list info_list_;
};
template<class Info_item>
std::ostream&
operator<<(std::ostream& os, const Info_set<Info_item>& info)
{
if ( info.is_empty() ) {
return os << "{}";
}
typedef typename Info_set<Info_item>::Info_item_iterator iterator;
iterator last = --info.info_items_end();
os << "{";
for (iterator it = info.info_items_begin(); it != last; ++it) {
os << *it << ", ";
}
os << *last << "}";
return os;
}
template<class Info_item_t>
struct Info_set_convert_info
{
typedef Info_item_t Info_item;
typedef const Info_set<Info_item>& result_type;
inline
result_type operator()(const Info_set<Info_item>& info0, bool) const
{
return info0;
}
inline
result_type operator()(const Info_set<Info_item>& info0,
const Info_set<Info_item>& , bool) const
{
return info0;
}
};
template<class Info_item_t>
struct Info_set_merge_info
{
typedef Info_item_t Info_item;
typedef Info_set<Info_item> result_type;
inline
Info_set<Info_item> operator()(const Info_set<Info_item>& info0,
const Info_set<Info_item>& info1) const
{
typedef typename Info_set<Info_item>::Info_list Info_list;
Info_list info_union = info0.info_list();
Info_list copy = info1.info_list();
info_union.splice(info_union.end(), copy);
return info_union;
}
};
struct Generate_info
{
static unsigned int ctr;
template<class Site>
std::string operator()(const Site& t) const
{
if ( t.is_point() ) {
char c = 'A' + ctr++;
return std::string(1, c);
}
char c1 = 'A' + ctr++;
char c2 = 'A' + ctr++;
return std::string(1, c1) + std::string(1, c2);
}
};
unsigned int Generate_info::ctr = 0;
#include <CGAL/Simple_cartesian.h>
#include <CGAL/Segment_Delaunay_graph_Linf_hierarchy_2.h>
#include <CGAL/Segment_Delaunay_graph_Linf_filtered_traits_2.h>
#include <CGAL/Segment_Delaunay_graph_storage_traits_with_info_2.h>
typedef std::string Info_item;
typedef Info_set<Info_item> Info;
typedef Info_set_convert_info<Info_item> Convert_info;
typedef Info_set_merge_info<Info_item> Merge_info;
typedef
CGAL::Segment_Delaunay_graph_storage_traits_with_info_2<Gt,
Info,
Convert_info,
Merge_info>
ST;
typedef SDG2::Finite_vertices_iterator FVIT;
typedef SDG2::Site_2 Site_2;
int main( int argc, char *argv[] )
{
if ( ! (( argc == 1 ) || (argc == 2)) ) {
std::cout <<"usage: "<< argv[0] <<" [filename]\n";
}
std::ifstream ifs( (argc == 1) ? "data/sitesxx.cin" : argv[1] );
assert( ifs );
SDG2 sdg;
Site_2 site;
Generate_info generate;
std::cout << std::endl;
std::cout << "Input sites:" << std::endl;
std::cout << "------------" << std::endl;
while ( ifs >> site ) {
Info info = generate(site);
std::cout << site << std::flush;
std::cout << "\r\t\t\t" << info << std::endl;
sdg.insert(site, info);
}
std::cout << std::endl;
assert( sdg.is_valid(true) );
std::cout << std::endl;
std::cout << "Output sites:" << std::endl;
std::cout << "-------------" << std::endl;
for (FVIT it = sdg.finite_vertices_begin();
it != sdg.finite_vertices_end(); ++it) {
if ( it->site().is_point() ) {
std::cout << it->site() << std::flush;
std::cout << "\r\t\t\t" << it->storage_site().info() << std::endl;
}
}
for (FVIT it = sdg.finite_vertices_begin();
it != sdg.finite_vertices_end(); ++it) {
if ( it->site().is_segment() ) {
std::cout << it->site() << std::flush;
std::cout << "\r\t\t\t" << it->storage_site().info() << std::endl;
}
}
std::cout << std::endl;
return 0;
}