Vcsn  2.1
Be Rational
algorithm.hh
Go to the documentation of this file.
1 #pragma once
2 
3 #include <boost/range/iterator_range_core.hpp>
4 
5 #include <algorithm>
6 #include <iterator> // next
7 
8 namespace vcsn
9 {
10  namespace detail
11  {
12  // Not in Boost 1.49.
13  template <typename Range, typename Predicate>
14  bool any_of(const Range &r, Predicate p)
15  {
16  using std::begin;
17  using std::end;
18  return std::any_of(begin(r), end(r), p);
19  }
20 
24  template <typename Container>
25  typename Container::value_type
26  back(const Container& container)
27  {
28  using std::begin;
29  using std::end;
30  auto i = begin(container);
31  auto iend = end(container);
32  assert(i != iend);
33  auto res = *i;
34  for (++i; i != iend; ++i)
35  res = *i;
36  return res;
37  }
38 
39  template< typename Container, typename Predicate>
40  void erase_if(Container& c, const Predicate& p)
41  {
42  using std::begin;
43  using std::end;
44  for (auto i = begin(c); i != end(c); /* nothing. */)
45  {
46  if (p(*i))
47  i = c.erase(i);
48  else
49  ++i;
50  }
51  }
52 
53 
55  template <typename Container>
56  typename Container::value_type
57  front(const Container& container)
58  {
59  using std::begin;
60  using std::end;
61  auto i = begin(container);
62  assert(i != end(container));
63  return *i;
64  }
65 
68  template <typename Iterator, typename Pred, typename Less>
69  boost::iterator_range<Iterator>
70  initial_sorted_range(Iterator begin, Iterator end,
71  Pred pred, Less less)
72  {
73  if (pred(*begin))
74  for (auto i = begin;; ++i)
75  {
76  auto next = std::next(i);
77  if (next == end
78  || !pred(*next)
79  || less(*next, *i))
80  return {begin, next};
81  }
82  else
83  return {end, end};
84  }
85 
90  template <typename Container, typename Compare>
91  bool is_sorted_forward(const Container& container, Compare comp)
92  {
93  auto i = std::begin(container);
94  auto end = std::end(container);
95  if (i != end)
96  {
97  auto prev = *i;
98  for (++i; i != end; ++i)
99  if (comp(prev, *i))
100  prev = *i;
101  else
102  return false;
103  }
104  return true;
105  }
106 
109  template <typename Container>
110  typename Container::value_type
111  max_forward(const Container& container)
112  {
113  auto i = std::begin(container);
114  auto end = std::end(container);
115  assert(i != end);
116  if (i != end)
117  {
118  auto res = *i;
119  for (++i; i != end; ++i)
120  if (res < *i)
121  res = *i;
122  return res;
123  }
124  abort();
125  }
126 
130  template <typename InputIt1, typename InputIt2>
131  std::pair<InputIt1, InputIt2>
132  mismatch(InputIt1 first1, InputIt1 last1,
133  InputIt2 first2, InputIt2 last2)
134  {
135  while (first1 != last1
136  && first2 != last2
137  && *first1 == *first2)
138  {
139  ++first1;
140  ++first2;
141  }
142  return std::make_pair(first1, first2);
143  }
144 
145  // Boost 1.49 does not have boost/algorithm/cxx11/none_of.hpp and the like.
146  template <typename Range, typename Predicate>
147  bool none_of(const Range &r, Predicate p)
148  {
149  using std::begin;
150  using std::end;
151  return std::none_of(begin(r), end(r), p);
152  }
153 
154  // Not in Boost 1.49.
155  template <typename Range, typename Value>
156  bool none_of_equal(const Range &r, const Value& value)
157  {
158  return none_of(r, [&value](const Value& v) { return v == value; });
159  }
160  }
161 
163  template <typename Container>
164  bool
165  same_domain(const Container& x, const Container& y)
166  {
167  if (x.size() != y.size())
168  return false;
169  // FIXME: no cbegin etc. in C++11.
170  using std::begin; using std::end;
171  for (auto xi = begin(x), xend = end(x), yi = begin(y);
172  xi != xend;
173  ++xi, ++yi)
174  if (x.key_comp()(xi->first, yi->first)
175  || x.key_comp()(yi->first, xi->first))
176  return false;
177  return true;
178  }
179 }
Container::value_type front(const Container &container)
The first member of this Container.
Definition: algorithm.hh:57
bool any_of(const Range &r, Predicate p)
Definition: algorithm.hh:14
Container::value_type back(const Container &container)
The last member of this Container.
Definition: algorithm.hh:26
Functor to compare Values of ValueSets.
Definition: functional.hh:72
bool is_sorted_forward(const Container &container, Compare comp)
Same as std::is_sorted, but works with an input iterator, not just a forward iterator.
Definition: algorithm.hh:91
std::pair< InputIt1, InputIt2 > mismatch(InputIt1 first1, InputIt1 last1, InputIt2 first2, InputIt2 last2)
Same as C++14's mismatch, which is not available in G++-4.8 with -std=c++1y.
Definition: algorithm.hh:132
void erase_if(Container &c, const Predicate &p)
Definition: algorithm.hh:40
Provide a variadic mul on top of a binary mul(), and one().
Definition: fwd.hh:46
bool none_of_equal(const Range &r, const Value &value)
Definition: algorithm.hh:156
bool none_of(const Range &r, Predicate p)
Definition: algorithm.hh:147
bool same_domain(const Container &x, const Container &y)
Check that two associative containers have the same keys.
Definition: algorithm.hh:165
boost::iterator_range< Iterator > initial_sorted_range(Iterator begin, Iterator end, Pred pred, Less less)
The return the longest initial range of elements matching the predicate.
Definition: algorithm.hh:70
Container::value_type max_forward(const Container &container)
Same as *std::max_element, but works with an input iterator, not just a forward iterator.
Definition: algorithm.hh:111