PerceMon
All Classes Namespaces Functions Variables Pages
topo.hpp
1
5#pragma once
6
7#ifndef __PERCEMON_TOPO_HPP__
8#define __PERCEMON_TOPO_HPP__
9
10#include <algorithm>
11#include <cstddef>
12#include <initializer_list>
13#include <memory>
14#include <set>
15#include <variant>
16#include <vector>
17
18#include "percemon/datastream.hpp"
19
31namespace percemon::topo {
32// TODO: Make this more abstract and able to handle general sets.
33
34struct Empty;
35struct Universe;
36struct BoundingBox;
37struct TopoUnion;
38
39struct Empty {};
40
41struct Universe {};
42
44 // NOTE: The origin in an image is the top left corner.
45 double xmin;
46 double xmax;
47 double ymin;
48 double ymax;
49
50 // Are left, right, top, or bottom boundaries open?
51 bool lopen = false;
52 bool ropen = false;
53 bool topen = false;
54 bool bopen = false;
55
56 BoundingBox() = delete;
57 BoundingBox(const BoundingBox&) = default;
58 BoundingBox(BoundingBox&&) = default;
59 BoundingBox& operator=(const BoundingBox&) = default;
60 BoundingBox& operator=(BoundingBox&&) = default;
61
63 double xmin_,
64 double xmax_,
65 double ymin_,
66 double ymax_,
67 bool lopen_ = false,
68 bool ropen_ = false,
69 bool topen_ = false,
70 bool bopen_ = false) :
71 xmin{xmin_},
72 xmax{xmax_},
73 ymin{ymin_},
74 ymax{ymax_},
75 lopen{lopen_},
76 ropen{ropen_},
77 topen{topen_},
78 bopen{bopen_} {};
79
81 BoundingBox{static_cast<double>(bbox.xmin),
82 static_cast<double>(bbox.xmax),
83 static_cast<double>(bbox.ymin),
84 static_cast<double>(bbox.ymax)} {};
85
87 xmin = bbox.xmin;
88 xmax = bbox.xmax;
89 ymin = bbox.ymin;
90 ymax = bbox.ymax;
91 return *this;
92 }
93};
94
95struct TopoUnion {
96 struct BBoxCmp {
97 constexpr bool operator()(const BoundingBox& a, const BoundingBox& b) const {
98 // TODO: Handling of open and closed sets?
99 if (a.xmin < b.xmin) { return true; }
100 if (a.xmin == b.xmin) {
101 if (a.xmax < b.xmax) { return true; }
102 if (a.xmax == b.xmax) {
103 if (a.ymin < b.ymin) { return true; }
104 if (a.ymin == b.ymin) {
105 if (a.ymax < b.ymax) { return true; }
106 }
107 }
108 }
109 return false;
110 }
111 };
112
113 using Set = std::set<BoundingBox, BBoxCmp>;
114 using value_type = BoundingBox;
115 using reference = BoundingBox&;
116 using const_reference = const BoundingBox&;
117 using iterator = Set::iterator;
118 using const_iterator = Set::const_iterator;
119 using difference_type = Set::difference_type;
120 using size_type = Set::size_type;
121
122 TopoUnion() = default;
123 TopoUnion(const TopoUnion&) = default;
124 TopoUnion(TopoUnion&&) = default;
125 TopoUnion& operator=(const TopoUnion&) = default;
126 TopoUnion& operator=(TopoUnion&&) = default;
127
128 template <typename Iter>
129 TopoUnion(Iter first, Iter last) : regions{first, last} {};
130
131 void insert(BoundingBox bbox) { regions.insert(bbox); }
132 void merge(const TopoUnion& other) {
133 std::merge(
134 regions.begin(),
135 regions.end(),
136 other.begin(),
137 other.end(),
138 std::inserter(regions, regions.begin()),
139 BBoxCmp{});
140 }
141
142 iterator begin() { return regions.begin(); }
143 [[nodiscard]] const_iterator begin() const { return regions.begin(); }
144 iterator end() { return regions.end(); }
145 [[nodiscard]] const_iterator end() const { return regions.end(); }
146
147 auto size() { return regions.size(); }
148
149 private:
150 Set regions;
151};
152
153using Region = std::variant<Empty, Universe, BoundingBox, TopoUnion>;
154using RegionPtr = std::shared_ptr<Region>;
155
156bool is_closed(const Region& region);
157bool is_open(const Region& region);
158double area(const Region& region);
159Region interior(const Region& region);
160Region closure(const Region& region);
161Region spatial_complement(const Region& region, const BoundingBox& universe);
162Region spatial_intersect(const Region& lhs, const Region& rhs);
163Region spatial_intersect(const std::vector<Region>&);
164Region spatial_union(const Region& lhs, const Region& rhs);
165Region spatial_union(const std::vector<Region>&);
166
167Region simplify_region(const Region& region);
168
169} // namespace percemon::topo
170
171#endif /* end of include guard: __PERCEMON_TOPO_HPP__ */
Definition: topo.hpp:31
Definition: datastream.hpp:37
Definition: topo.hpp:43
Definition: topo.hpp:39
Definition: topo.hpp:96
Definition: topo.hpp:95
Definition: topo.hpp:41