/
types.h
102 lines (82 loc) · 4.74 KB
/
types.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
#ifndef TYPES_H_BY7A88L9
#define TYPES_H_BY7A88L9
#include <oak/oak.h>
#include <oak/debug.h>
namespace ng
{
struct PUBLIC index_t
{
index_t () : index(SIZE_T_MAX), carry(SIZE_T_MAX) { }
index_t (size_t index, size_t carry = 0) : index(index), carry(carry) { }
explicit operator bool () const { return index != SIZE_T_MAX; }
bool operator== (index_t const& rhs) const { return index == rhs.index && carry == rhs.carry; }
bool operator!= (index_t const& rhs) const { return !(*this == rhs); }
bool operator< (index_t const& rhs) const { return index < rhs.index || index == rhs.index && carry < rhs.carry; }
bool operator<= (index_t const& rhs) const { return *this < rhs || *this == rhs; }
index_t operator+ (ssize_t i) const { return index_t(index + i, carry); }
size_t index;
size_t carry;
};
struct PUBLIC range_t
{
range_t () : columnar(false), freehanded(false), unanchored(false) { }
range_t (index_t first, index_t last = index_t(), bool columnar = false, bool freehanded = false, bool unanchored = false) : first(first), last(last ?: first), columnar(columnar), freehanded(last ? freehanded : first.carry != 0), unanchored(unanchored) { }
index_t& min () { return first < last ? first : last; }
index_t& max () { return first < last ? last : first; }
index_t const& min () const { return first < last ? first : last; }
index_t const& max () const { return first < last ? last : first; }
range_t sorted () const { return range_t(min(), max(), columnar, freehanded); }
bool empty () const { return freehanded ? first == last : first.index == last.index; }
explicit operator bool () const { return first ? true : false; }
bool operator== (range_t const& tmp) const { auto lhs = normalized(), rhs = tmp.normalized(); return lhs.first == rhs.first && lhs.last == rhs.last && lhs.columnar == rhs.columnar && lhs.freehanded == rhs.freehanded; }
bool operator!= (range_t const& tmp) const { auto lhs = normalized(), rhs = tmp.normalized(); return lhs.first != rhs.first || lhs.last != rhs.last || lhs.columnar != rhs.columnar || lhs.freehanded != rhs.freehanded; }
bool operator< (range_t const& tmp) const { auto lhs = normalized(), rhs = tmp.normalized(); return lhs.first < rhs.first || lhs.first == rhs.first && lhs.last < rhs.last; }
range_t operator+ (ssize_t i) const { return range_t(first + i, last + i, columnar, freehanded); }
range_t& operator= (index_t const& rhs) { first = last = rhs; return *this; }
index_t first, last;
bool columnar, freehanded, unanchored;
private:
range_t normalized () const
{
bool strip = !columnar && !freehanded;
return range_t(strip ? min().index : min(), strip ? max().index : max(), columnar, freehanded, unanchored);
}
};
struct PUBLIC ranges_t
{
typedef range_t value_type;
typedef std::vector<range_t>::iterator iterator;
typedef std::vector<range_t>::const_iterator const_iterator;
ranges_t () { }
ranges_t (index_t const& first) : ranges(1, range_t(first, first)) { }
ranges_t (range_t const& range) : ranges(1, range) { }
bool operator== (ranges_t const& rhs) const { return ranges == rhs.ranges; }
bool operator!= (ranges_t const& rhs) const { return ranges != rhs.ranges; }
bool empty () const { return ranges.empty(); }
size_t size () const { return ranges.size(); }
explicit operator bool () const { return !empty(); }
void push_back (range_t const& r) { ranges.push_back(r); }
void push_back (index_t const& index) { push_back(range_t(index, index)); }
iterator begin () { return ranges.begin(); }
iterator end () { return ranges.end(); }
const_iterator begin () const { return ranges.begin(); }
const_iterator end () const { return ranges.end(); }
range_t& first () { ASSERT(!empty()); return ranges.front(); }
range_t const& first () const { ASSERT(!empty()); return ranges.front(); }
range_t& last () { ASSERT(!empty()); return ranges.back(); }
range_t const& last () const { ASSERT(!empty()); return ranges.back(); }
ranges_t sorted () const
{
std::vector<range_t> tmp(ranges);
std::sort(tmp.begin(), tmp.end());
return tmp;
}
private:
ranges_t (std::vector<range_t> const& ranges) : ranges(ranges) { }
std::vector<range_t> ranges;
};
PUBLIC std::string to_s (index_t const& index);
PUBLIC std::string to_s (range_t const& range);
PUBLIC std::string to_s (ranges_t const& ranges);
} /* ng */
#endif /* end of include guard: TYPES_H_BY7A88L9 */