carl  24.04
Computer ARithmetic Library
Sampling.h
Go to the documentation of this file.
1 #pragma once
2 
3 #include "Interval.h"
4 
5 namespace carl {
6 
7 /**
8  * Returns the center point of the interval.
9  * @return Center.
10  */
11 template<typename Number>
12 Number center(const Interval<Number>& i) {
13  assert(i.is_consistent() && !i.is_empty());
14  if (i.is_infinite()) return carl::constant_zero<Number>().get();
17  }
20  }
21  return boost::numeric::median(i.content());
22 }
23 
24 /**
25  * Searches for some point in this interval, preferably near the midpoint and with a small representation.
26  * Checks the integers next to the midpoint, uses the midpoint if both are outside.
27  * @return Some point within this interval.
28  */
29 template<typename Number>
30 Number sample(const Interval<Number>& i, bool includingBounds = true) {
31  assert(i.is_consistent() && !i.is_empty());
32  assert(includingBounds || !i.is_point_interval());
33  Number mid = center(i);
34  if (Number midf = carl::floor(mid); i.contains(midf) && (includingBounds || i.lower_bound_type() == BoundType::INFTY || i.lower() < midf)) {
35  return midf;
36  }
37  if (Number midc = carl::ceil(mid); i.contains(midc) && (includingBounds || i.upper_bound_type() == BoundType::INFTY || i.upper() > midc)) {
38  return midc;
39  }
40  return mid;
41 }
42 
43 /**
44  * Searches for some point in this interval, preferably near the midpoint and with a small representation.
45  * Uses a binary search based on the Stern-Brocot tree starting from the integer below the midpoint.
46  * @return Some point within this interval.
47  */
48 template<typename Number>
49 Number sample_stern_brocot(const Interval<Number>& i, bool includingBounds = true) {
50  assert(i.is_consistent() && !i.is_empty());
51 
52  using Int = typename carl::IntegralType<Number>::type;
53  Int leftnum = Int(carl::floor(center(i)));
54  Int leftden = carl::constant_one<Int>::get();
55  Int rightnum = carl::constant_one<Int>::get();
56  Int rightden = carl::constant_zero<Int>::get();
57  Number cur = Number(leftnum) / Number(leftden);
58  if (i.contains(cur)) {
59  return cur;
60  }
61  while (true) {
62  Int curnum = leftnum + rightnum;
63  Int curden = leftden + rightden;
64  cur = Number(curnum) / Number(curden);
65  if ((cur < i.lower()) || (!includingBounds && cur == i.lower())) {
66  leftnum = curnum;
67  leftden = curden;
68  } else if ((cur > i.upper()) || (!includingBounds && cur == i.upper())) {
69  rightnum = curnum;
70  rightden = curden;
71  } else {
72  return cur;
73  }
74  }
75 }
76 
77 /**
78  * Searches for some point in this interval, preferably near the left endpoint and with a small representation.
79  * Checks the integer next to the left endpoint, uses the midpoint if it is outside.
80  * @return Some point within this interval.
81  */
82 template<typename Number>
83 Number sample_left(const Interval<Number>& i) {
84  assert(i.is_consistent() && !i.is_empty());
87  }
88  Number res = carl::floor(i.lower()) + carl::constant_one<Number>().get();
89  if (i.contains(res)) return res;
90  return center(i);
91 }
92 /**
93  * Searches for some point in this interval, preferably near the right endpoint and with a small representation.
94  * Checks the integer next to the right endpoint, uses the midpoint if it is outside.
95  * @return Some point within this interval.
96  */
97 template<typename Number>
98 Number sample_right(const Interval<Number>& i) {
99  assert(i.is_consistent() && !i.is_empty());
100  if (i.upper_bound_type() == BoundType::INFTY) {
102  }
103  Number res = carl::ceil(i.upper()) - carl::constant_one<Number>().get();
104  if (i.contains(res)) return res;
105  return center(i);
106 }
107 /**
108 * Searches for some point in this interval, preferably near zero and with a small representation.
109 * Checks the integer next to the left endpoint if the interval is semi-positive.
110 * Checks the integer next to the right endpoint if the interval is semi-negative.
111 * Uses zero otherwise.
112 * @return Some point within this interval.
113 */
114 template<typename Number>
115 Number sample_zero(const Interval<Number>& i) {
116  assert(i.is_consistent() && !i.is_empty());
117  if (i.is_semi_positive()) return sample_left(i);
118  if (i.is_semi_negative()) return sample_right(i);
120 }
121 /**
122 * Searches for some point in this interval, preferably far aways from zero and with a small representation.
123 * Checks the integer next to the right endpoint if the interval is semi-positive.
124 * Checks the integer next to the left endpoint if the interval is semi-negative.
125 * Uses zero otherwise.
126 * @return Some point within this interval.
127 */
128 template<typename Number>
129 Number sample_infty(const Interval<Number>& i) {
130  assert(i.is_consistent() && !i.is_empty());
131  if (i.is_semi_positive()) return sample_right(i);
132  if (i.is_semi_negative()) return sample_left(i);
134 }
135 
136 
137 }
carl is the main namespace for the library.
Number sample_infty(const Interval< Number > &i)
Searches for some point in this interval, preferably far aways from zero and with a small representat...
Definition: Sampling.h:129
Number sample_left(const Interval< Number > &i)
Searches for some point in this interval, preferably near the left endpoint and with a small represen...
Definition: Sampling.h:83
Interval< Number > ceil(const Interval< Number > &_in)
Method which returns the next larger integer of the passed number or the number itself,...
Definition: Interval.h:1535
Number sample(const Interval< Number > &i, bool includingBounds=true)
Searches for some point in this interval, preferably near the midpoint and with a small representatio...
Definition: Sampling.h:30
Number center(const Interval< Number > &i)
Returns the center point of the interval.
Definition: Sampling.h:12
Number sample_zero(const Interval< Number > &i)
Searches for some point in this interval, preferably near zero and with a small representation.
Definition: Sampling.h:115
Interval< Number > floor(const Interval< Number > &_in)
Method which returns the next smaller integer of this number or the number itself,...
Definition: Interval.h:1523
Number sample_stern_brocot(const Interval< Number > &i, bool includingBounds=true)
Searches for some point in this interval, preferably near the midpoint and with a small representatio...
Definition: Sampling.h:49
Number sample_right(const Interval< Number > &i)
Searches for some point in this interval, preferably near the right endpoint and with a small represe...
Definition: Sampling.h:98
@ INFTY
the given bound is interpreted as minus or plus infinity depending on whether it is the left or the r...
The class which contains the interval arithmetic including trigonometric functions.
Definition: Interval.h:134
bool is_empty() const
Function which determines, if the interval is empty.
Definition: Interval.h:1056
BoundType lower_bound_type() const
The getter for the lower bound type of the interval.
Definition: Interval.h:883
const BoostInterval & content() const
Returns a reference to the included boost interval.
Definition: Interval.h:865
const Number & upper() const
The getter for the upper boundary of the interval.
Definition: Interval.h:849
bool is_semi_positive() const
Definition: Interval.h:1146
bool contains(const Number &val) const
Checks if the interval contains the given value.
const Number & lower() const
The getter for the lower boundary of the interval.
Definition: Interval.h:840
bool is_point_interval() const
Function which determines, if the interval is a pointinterval.
Definition: Interval.h:1071
bool is_semi_negative() const
Definition: Interval.h:1157
bool is_consistent() const
A quick check for the bound values.
Definition: Interval.h:1426
BoundType upper_bound_type() const
The getter for the upper bound type of the interval.
Definition: Interval.h:892
bool is_infinite() const
Function which determines, if the interval is (-oo,oo).
Definition: Interval.h:1026
static const T & get()
Definition: constants.h:42
static const T & get()
Definition: constants.h:51