8 #ifndef Sawyer_IntervalSet_H
9 #define Sawyer_IntervalSet_H
11 #include <Sawyer/IntervalMap.h>
12 #include <Sawyer/Optional.h>
13 #include <Sawyer/Sawyer.h>
15 #include <boost/integer_traits.hpp>
16 #include <boost/iterator/iterator_facade.hpp>
17 #include <boost/serialization/access.hpp>
18 #include <boost/serialization/nvp.hpp>
61 friend class boost::serialization::access;
64 void serialize(S &s,
const unsigned ) {
65 s & BOOST_SERIALIZATION_NVP(map_);
77 boost::bidirectional_traversal_tag> {
79 MapNodeIterator iter_;
83 friend class boost::iterator_core_access;
86 const Interval& dereference()
const {
return iter_->key(); }
88 void increment() { ++iter_; }
89 void decrement() { --iter_; }
90 MapNodeIterator base()
const {
return iter_; }
100 class ConstScalarIterator:
public boost::iterator_facade<ConstScalarIterator, const typename Interval::Value,
101 boost::bidirectional_traversal_tag> {
109 friend class boost::iterator_core_access;
112 ASSERT_require2(iter_->least() <= iter_->greatest(),
"stored interval cannot be empty");
113 ASSERT_require(iter_->least() + offset_ <= iter_->
greatest());
114 value_ = iter_->least() + offset_;
118 return iter_ == other.iter_ && offset_ == other.offset_;
121 ASSERT_require2(iter_->least() <= iter_->greatest(),
"stored interval cannot be empty");
122 if (iter_->least() + offset_ == iter_->greatest()) {
130 ASSERT_require2(iter_->least() <= iter_->greatest(),
"stored interval cannot be empty");
133 offset_ = width(*iter_);
152 template<
class Interval2>
155 for (OtherIntervalIterator otherIter=other.
intervals().begin(); otherIter!=other.
intervals().end(); ++otherIter)
163 template<
class Interval2,
class T,
class Policy>
166 for (OtherNodeIterator otherIter=other.
nodes().begin(); otherIter!=other.
nodes().end(); ++otherIter)
174 template<
class Iterator>
184 template<
class Interval2>
188 for (OtherIntervalIterator otherIter=other.
intervals().begin(); otherIter!=other.
intervals().end(); ++otherIter)
199 template<
class Interval2,
class T,
class Policy>
203 for (OtherNodeIterator otherIter=other.
nodes().begin(); otherIter!=other.
nodes().end(); ++otherIter)
212 template<
class Iterator>
225 boost::iterator_range<ConstIntervalIterator>
intervals()
const {
226 return boost::iterator_range<ConstIntervalIterator>(ConstIntervalIterator(map_.
nodes().begin()),
227 ConstIntervalIterator(map_.
nodes().end()));
231 boost::iterator_range<ConstScalarIterator>
scalars()
const {
232 return boost::iterator_range<ConstScalarIterator>(ConstScalarIterator(
intervals().begin()),
240 return ConstIntervalIterator(map_.
lowerBound(scalar));
247 return ConstIntervalIterator(map_.
upperBound(scalar));
254 return ConstIntervalIterator(map_.
findPrior(scalar));
261 return ConstIntervalIterator(map_.
find(scalar));
267 boost::iterator_range<ConstIntervalIterator>
findAll(
const Interval &interval)
const {
268 boost::iterator_range<typename Map::ConstNodeIterator> range = map_.
findAll(interval);
269 return boost::iterator_range<ConstIntervalIterator>(ConstIntervalIterator(range.begin()),
270 ConstIntervalIterator(range.end()));
285 std::pair<ConstIntervalIterator, ConstIntervalIterator>
287 std::pair<typename Map::ConstNodeIterator, typename Map::ConstNodeIterator> found =
289 return std::make_pair(ConstIntervalIterator(found.first), ConstIntervalIterator(found.second));
334 template<
class Interval2>
336 return map_.isOverlapping(interval);
339 template<
class Interval2>
341 return map_.isOverlapping(other.map_);
344 template<
class Interval2,
class T2,
class Policy2>
346 return map_.isOverlapping(other);
355 template<
class Interval2>
360 template<
class Interval2>
365 template<
class Interval2,
class T2,
class Policy2>
387 template<
class Interval2>
389 return map_.contains(interval);
392 template<
class Interval2>
394 return map_.contains(other.map_);
397 template<
class Interval2,
class T2,
class Policy2>
399 return map_.contains(other);
424 return map_.
least(lowerLimit);
461 return ConstIntervalIterator(map_.
firstFit(
size, start.iter_));
475 return ConstIntervalIterator(map_.
bestFit(
size, start.iter_));
501 void invert(
const Interval &restricted) {
503 if (!restricted.isEmpty()) {
505 bool insertTop =
true;
508 if (iter->least() > restricted.greatest())
510 if (pending < iter->
least())
512 if (iter->greatest() < restricted.greatest()) {
513 pending = iter->greatest() + 1;
522 std::swap(map_, inverted.map_);
531 template<
class Interval2>
536 template<
class Interval2>
539 for (OtherIterator otherIter=other.
intervals().begin(); otherIter!=other.
intervals().end(); ++otherIter)
540 map_.
insert(*otherIter, 0);
543 template<
class Interval2,
class T,
class Policy>
546 for (OtherIterator otherIter=other.
intervals().begin(); otherIter!=other.
intervals().end(); ++otherIter)
547 map_.
insert(*otherIter, 0);
557 template<
class Interval2>
558 void erase(
const Interval2 &interval) {
559 map_.
erase(interval);
562 template<
class Interval2>
564 ASSERT_forbid2((
void*)&other==(
void*)
this,
"use IntervalSet::clear() instead");
566 for (OtherIntervalIterator otherIter=other.
intervals().begin(); otherIter!=other.
intervals().end(); ++otherIter)
567 map_.
erase(*otherIter);
570 template<
class Interval2,
class T,
class Policy>
573 for (OtherIntervalIterator otherIter=other.
intervals().begin(); otherIter!=other.
intervals().end(); ++otherIter)
574 map_.
erase(otherIter->first);
585 template<
class Interval2>
589 if (interval.isEmpty()) {
599 template<
class Interval2>
605 template<
class Interval2,
class T,
class Policy>
616 return !(*
this!=other);
void eraseMultiple(const IntervalMap< Interval, T2, Policy2 > &other)
Erase intervals specified in another IntervalMap.
Holds a value or nothing.
Interval hull() const
Returns the range of values in this map.
A container holding a set of values.
I::Value Scalar
Type of scalar values stored in this set.
bool operator==(const IntervalSet &other) const
Determines if two sets contain the same elements.
ConstIntervalIterator bestFit(const typename Interval::Value &size, ConstIntervalIterator start) const
Find the best fit node at or after a starting point.
Optional< typename Interval::Value > greatestUnmapped(typename Interval::Value upperLimit) const
Returns the limited-maximum unmapped scalar key.
boost::iterator_range< NodeIterator > nodes()
Iterators for traversing nodes.
ConstIntervalIterator firstFit(const typename Interval::Value &size, ConstIntervalIterator start) const
Find the first fit node at or after a starting point.
bool isOverlapping(const Interval2 &interval) const
Determines whether this set overlaps with the argument.
Interval::Value size() const
Number of scalar elements represented.
NodeIterator find(const typename Interval::Value &scalar)
Find the node containing the specified scalar key.
bool isOverlapping(const IntervalSet< Interval2 > &other) const
Determines whether this set overlaps with the argument.
void intersect(const Interval2 &interval)
Interset with specified values.
std::pair< ConstIntervalIterator, ConstIntervalIterator > findFirstOverlap(ConstIntervalIterator thisIter, const IntervalSet &other, ConstIntervalIterator otherIter) const
Find first nodes that overlap.
IntervalSet()
Default constructor.
T Value
Types of values in the interval.
Optional< Scalar > least(Scalar lowerLimit) const
Returns the limited-minimum scalar contained in this set.
Scalar least() const
Returns the minimum scalar contained in this set.
boost::iterator_range< ConstIntervalIterator > intervals() const
Iterators for traversing keys.
Bidirectional iterator over keys.
static Interval whole()
Construct an interval that covers the entire domain.
void erase(const Interval2 &interval)
Remove specified values.
IntervalSet operator~() const
Return inverse of specified set.
bool contains(const IntervalSet< Interval2 > &other) const
Determines whether this set fully contains the argument.
IntervalSet & operator-=(const Interval &interval)
In-place subtraction of an interval.
bool contains(const Interval2 &interval) const
Determines whether this set fully contains the argument.
bool isEmpty() const
Determine whether the container is empty.
Interval::Value greatest() const
Returns the maximum scalar key.
IntervalSet & operator=(const IntervalSet< Interval2 > &other)
Assignment from another set.
void eraseMultiple(const IntervalSet< Interval2 > &other)
Remove specified values.
ConstIntervalIterator find(const typename Interval::Value &scalar) const
Find the node containing the specified scalar key.
IntervalSet operator&(const Interval &interval) const
Intersection of set with interval.
bool isOverlapping(const IntervalMap< Interval2, T2, Policy2 > &other) const
Determines whether this set overlaps with the argument.
void insert(const Interval2 &interval)
Insert specified values.
bool exists(const typename Interval::Value &scalar) const
Determines if a value exists in the set.
boost::iterator_range< ConstIntervalIterator > intervals() const
Iterator range for all intervals actually stored by this set.
bool contains(const IntervalMap< Interval2, T2, Policy2 > &other) const
Determines whether this set fully contains the argument.
void erase(const Interval &erasure)
Erase the specified interval.
NodeIterator upperBound(const typename Interval::Value &scalar)
Find the first node whose interval begins above the specified scalar key.
bool operator!=(const IntervalSet &other) const
Determines if two sets contain different elements.
ConstIntervalIterator upperBound(const typename Interval::Value &scalar) const
Find the first node whose interval begins above the specified scalar key.
void clear()
Remove all values.
IntervalSet & operator=(const IntervalMap< Interval2, T, Policy > &other)
Assignment from an IntervalMap.
void intersect(IntervalSet< Interval2 > other)
Interset with specified values.
ConstIntervalIterator findPrior(const typename Interval::Value &scalar) const
Find the last node whose interval starts at or below the specified scalar key.
Bidirectional iterator over key/value nodes.
Interval hull() const
Returns the range of values in this map.
IntervalSet & operator|=(const IntervalSet &other)
In-place union.
IntervalSet(const IntervalSet< Interval2 > &other)
Copy constructor.
NodeIterator lowerBound(const typename Interval::Value &scalar)
Find the first node whose interval ends at or above the specified scalar key.
NodeIterator bestFit(const typename Interval::Value &size, NodeIterator start)
Find the best fit node at or after a starting point.
Scalar greatest() const
Returns the maximum scalar contained in this set.
Optional< Scalar > greatestNonExistent(Scalar upperLimit) const
Returns the limited-maximum scalar not contained in this set.
IntervalSet(const boost::iterator_range< Iterator > &intervals)
Construct from an iterator range.
bool isDistinct(const Interval2 &interval) const
Determines whether this set is distinct from the argument.
bool contains(const typename Interval::Value &scalar) const
Determines whether this set fully contains the argument.
IntervalSet operator&(const IntervalSet &other) const
Intersection of two sets.
IntervalSet & operator&=(const IntervalSet &other)
In-place intersection.
boost::iterator_range< ConstScalarIterator > scalars() const
Iterator range for all scalar values logically represented by this set.
NodeIterator findPrior(const typename Interval::Value &scalar)
Find the last node whose interval starts at or below the specified scalar key.
Name space for the entire library.
void insert(Interval key, Value value, bool makeHole=true)
Insert a key/value pair.
bool isDistinct(const IntervalMap< Interval2, T2, Policy2 > &other) const
Determines whether this set is distinct from the argument.
static Interval hull(T v1, T v2)
Construct an interval from two endpoints.
ConstIntervalIterator findFirstOverlap(const Interval &interval) const
Finds first node that overlaps with the specified interval.
bool isEmpty() const
Determine if the container is empty.
Interval::Value size() const
Returns the number of values represented by this container.
boost::iterator_range< ConstIntervalIterator > findAll(const Interval &interval) const
Finds all nodes overlapping the specified interval.
ConstIntervalIterator lowerBound(const typename Interval::Value &scalar) const
Find the first node whose interval ends at or above the specified scalar key.
bool isDistinct(const IntervalSet< Interval2 > &other) const
Determines whether this set is distinct from the argument.
size_t nIntervals() const
Number of nodes in the container.
IntervalSet(const IntervalMap< Interval2, T, Policy > &other)
Construct from an IntervalMap.
IntervalSet operator-(const IntervalSet &other) const
Subtract another set from this one.
Optional< typename Interval::Value > leastUnmapped(typename Interval::Value lowerLimit) const
Returns the limited-minimum unmapped scalar key.
size_t nIntervals() const
Number of storage nodes.
void invert(const Interval &restricted)
Invert and intersect.
void eraseMultiple(const IntervalMap< Interval2, T, Policy > &other)
Remove specified values.
NodeIterator findFirstOverlap(const Interval &interval)
Find first interval that overlaps with the specified interval.
IntervalSet & operator-=(const IntervalSet &other)
In-place subtraction.
void insertMultiple(const IntervalMap< Interval2, T, Policy > &other)
Insert specified values.
IntervalSet operator|(const Interval &interval) const
Union of set with interval.
Interval::Value least() const
Returns the minimum scalar key.
Optional< Scalar > greatest(Scalar upperLimit) const
Returns the limited-maximum scalar contained in this set.
IntervalSet operator|(const IntervalSet &other) const
Union of two sets.
Optional< Scalar > leastNonExistent(Scalar lowerLimit) const
Returns the limited-minimum scalar not contained in this set.
IntervalSet & operator&=(const Interval &interval)
In-place intersection with an interval.
void clear()
Empties the container.
IntervalSet operator-(const Interval &interval) const
Subtract an interval from this set.
IntervalSet & operator|=(const Interval &interval)
In-place union with interval.
NodeIterator firstFit(const typename Interval::Value &size, NodeIterator start)
Find the first fit node at or after a starting point.
boost::iterator_range< NodeIterator > findAll(const Interval &interval)
Finds all nodes overlapping the specified interval.
void insertMultiple(const IntervalSet< Interval2 > &other)
Insert specified values.
IntervalSet & operator=(const boost::iterator_range< Iterator > &intervals)
Assignment from an iterator range.