remove the range half stuff for now

master
Daniel Kolesa 2017-03-31 03:04:32 +02:00
parent 9d08f4361d
commit 6ddb0f1b17
2 changed files with 1 additions and 318 deletions

View File

@ -132,7 +132,7 @@ From forward ranges onwards, independence of state is guaranteed though.
This method checks whether the range has any elements left in it. If this This method checks whether the range has any elements left in it. If this
returns true, it means `front()` is safe to use. Safe code should always returns true, it means `front()` is safe to use. Safe code should always
check; the behavior is an item is retrieved on an empty range. check; the behavior is undefined if an item is retrieved on an empty range.
~~~{.cc} ~~~{.cc}
bool equals_front() const; bool equals_front() const;

View File

@ -250,227 +250,6 @@ namespace detail {
}; };
} }
// range half
template<typename T>
struct half_range;
namespace detail {
template<typename R, bool = is_bidirectional_range<typename R::range>>
struct range_add;
template<typename R>
struct range_add<R, true> {
using diff_t = range_difference_t<typename R::range>;
static diff_t add_n(R &half, diff_t n) {
if (n < 0) {
return -half.prev_n(n);
}
return half.next_n(n);
}
static diff_t sub_n(R &half, diff_t n) {
if (n < 0) {
return -half.next_n(n);
}
return half.prev_n(n);
}
};
template<typename R>
struct range_add<R, false> {
using diff_t = range_difference_t<typename R::range>;
static diff_t add_n(R &half, diff_t n) {
if (n < 0) {
return 0;
}
return half.next_n(n);
}
static diff_t sub_n(R &half, diff_t n) {
if (n < 0) {
return 0;
}
return half.prev_n(n);
}
};
}
namespace detail {
template<typename>
struct range_iterator_tag {
/* better range types all become random access iterators */
using type = std::random_access_iterator_tag;
};
template<>
struct range_iterator_tag<input_range_tag> {
using type = std::input_iterator_tag;
};
template<>
struct range_iterator_tag<output_range_tag> {
using type = std::output_iterator_tag;
};
template<>
struct range_iterator_tag<forward_range_tag> {
using type = std::forward_iterator_tag;
};
template<>
struct range_iterator_tag<bidirectional_range_tag> {
using type = std::bidirectional_iterator_tag;
};
}
template<typename T>
struct range_half {
private:
T p_range;
public:
using range = T;
using iterator_category = typename detail::range_iterator_tag<T>::type;
using value_type = range_value_t<T>;
using difference_type = range_difference_t<T>;
using pointer = range_value_t<T> *;
using reference = range_reference_t<T>;
range_half() = delete;
range_half(T const &range): p_range(range) {}
template<typename U, typename = std::enable_if_t<std::is_convertible_v<U, T>>>
range_half(range_half<U> const &half): p_range(half.p_range) {}
range_half(range_half const &half): p_range(half.p_range) {}
range_half(range_half &&half): p_range(std::move(half.p_range)) {}
range_half &operator=(range_half const &half) {
p_range = half.p_range;
return *this;
}
range_half &operator=(range_half &&half) {
p_range = std::move(half.p_range);
return *this;
}
void next() { p_range.pop_front(); }
void prev() { p_range.push_front(); }
void next_n(range_size_t<T> n) {
p_range.pop_front_n(n);
}
void prev_n(range_size_t<T> n) {
p_range.push_front_n(n);
}
range_difference_t<T> add_n(range_difference_t<T> n) {
return detail::range_add<range_half<T>>::add_n(*this, n);
}
range_difference_t<T> sub_n(range_difference_t<T> n) {
return detail::range_add<range_half<T>>::sub_n(*this, n);
}
range_reference_t<T> get() const {
return p_range.front();
}
range_difference_t<T> distance(range_half const &half) const {
return p_range.distance_front(half.p_range);
}
bool equals(range_half const &half) const {
return p_range.equals_front(half.p_range);
}
bool operator==(range_half const &half) const {
return equals(half);
}
bool operator!=(range_half const &half) const {
return !equals(half);
}
bool operator<(range_half const &half) const {
return distance(half) > 0;
}
bool operator>(range_half const &half) const {
return distance(half) < 0;
}
bool operator<=(range_half const &half) const {
return distance(half) >= 0;
}
bool operator>=(range_half const &half) const {
return distance(half) <= 0;
}
/* iterator like interface */
range_reference_t<T> operator*() const {
return p_range.front();
}
range_reference_t<T> operator[](range_size_t<T> idx) const {
return p_range[idx];
}
range_half &operator++() {
next();
return *this;
}
range_half operator++(int) {
range_half tmp(*this);
next();
return tmp;
}
range_half &operator--() {
prev();
return *this;
}
range_half operator--(int) {
range_half tmp(*this);
prev();
return tmp;
}
range_half operator+(range_difference_t<T> n) const {
range_half tmp(*this);
tmp.add_n(n);
return tmp;
}
range_half operator-(range_difference_t<T> n) const {
range_half tmp(*this);
tmp.sub_n(n);
return tmp;
}
range_half &operator+=(range_difference_t<T> n) {
add_n(n);
return *this;
}
range_half &operator-=(range_difference_t<T> n) {
sub_n(n);
return *this;
}
T iter() const { return p_range; }
half_range<range_half> iter(range_half const &other) const {
return half_range<range_half>(*this, other);
}
range_value_t<T> *data() { return p_range.data(); }
range_value_t<T> const *data() const { return p_range.data(); }
};
template<typename R>
inline range_difference_t<R> operator-(
range_half<R> const &lhs, range_half<R> const &rhs
) {
return rhs.distance(lhs);
}
namespace detail { namespace detail {
template<typename R> template<typename R>
void pop_front_n(R &range, range_size_t<R> n) { void pop_front_n(R &range, range_size_t<R> n) {
@ -581,10 +360,6 @@ struct input_range {
return zip_range<B, R1, RR...>(iter(), std::move(r1), std::move(rr)...); return zip_range<B, R1, RR...>(iter(), std::move(r1), std::move(rr)...);
} }
range_half<B> half() const {
return range_half<B>(iter());
}
/* iterator like interface operating on the front part of the range /* iterator like interface operating on the front part of the range
* this is sometimes convenient as it can be used within expressions */ * this is sometimes convenient as it can be used within expressions */
@ -851,98 +626,6 @@ namespace detail {
constexpr bool iterable_test = decltype(test_iterable<T>(0))::value; constexpr bool iterable_test = decltype(test_iterable<T>(0))::value;
} }
template<typename T>
struct half_range: input_range<half_range<T>> {
using range_category = range_category_t <typename T::range>;
using value_type = range_value_t <typename T::range>;
using reference = range_reference_t <typename T::range>;
using size_type = range_size_t <typename T::range>;
using difference_type = range_difference_t<typename T::range>;
private:
T p_beg;
T p_end;
public:
half_range() = delete;
half_range(half_range const &range):
p_beg(range.p_beg), p_end(range.p_end)
{}
half_range(half_range &&range):
p_beg(std::move(range.p_beg)), p_end(std::move(range.p_end))
{}
half_range(T const &beg, T const &end):
p_beg(beg),p_end(end)
{}
half_range(T &&beg, T &&end):
p_beg(std::move(beg)), p_end(std::move(end))
{}
half_range &operator=(half_range const &range) {
p_beg = range.p_beg;
p_end = range.p_end;
return *this;
}
half_range &operator=(half_range &&range) {
p_beg = std::move(range.p_beg);
p_end = std::move(range.p_end);
return *this;
}
bool empty() const { return p_beg == p_end; }
void pop_front() {
p_beg.next();
}
void push_front() {
p_beg.prev();
}
void pop_back() {
p_end.prev();
}
void push_back() {
p_end.next();
}
reference front() const { return *p_beg; }
reference back() const { return *(p_end - 1); }
bool equals_front(half_range const &range) const {
return p_beg == range.p_beg;
}
bool equals_back(half_range const &range) const {
return p_end == range.p_end;
}
difference_type distance_front(half_range const &range) const {
return range.p_beg - p_beg;
}
difference_type distance_back(half_range const &range) const {
return range.p_end - p_end;
}
size_type size() const { return p_end - p_beg; }
half_range slice(size_type start, size_type end) const {
return half_range{p_beg + start, p_beg + end};
}
reference operator[](size_type idx) const {
return p_beg[idx];
}
void put(value_type const &v) {
p_beg.range().put(v);
}
void put(value_type &&v) {
p_beg.range().put(std::move(v));
}
value_type *data() { return p_beg.data(); }
value_type const *data() const { return p_beg.data(); }
};
template<typename T> template<typename T>
struct reverse_range: input_range<reverse_range<T>> { struct reverse_range: input_range<reverse_range<T>> {
using range_category = std::common_type_t< using range_category = std::common_type_t<