38 template <std::ranges::View underlying_range_type>
59 template <
typename range_type>
65 template <
typename other_range_type>
67 friend class iterator_type;
90 using iterator_category = iterator_tag_t<underlying_iterator_type>;
96 constexpr iterator_type() noexcept = default;
97 constexpr iterator_type(iterator_type const &) noexcept = default;
98 constexpr iterator_type(iterator_type &&) noexcept = default;
99 constexpr iterator_type & operator=(iterator_type const &) noexcept = default;
100 constexpr iterator_type & operator=(iterator_type &&) noexcept = default;
101 ~iterator_type() noexcept = default;
115 constexpr iterator_type(underlying_iterator_type iter,
116 underlying_iterator_type begin_it,
117 underlying_iterator_type end_it) noexcept :
132 template <std::ConvertibleTo<range_type &> other_range_type>
134 constexpr iterator_type(iterator_type<other_range_type> other) noexcept :
135 iterator_type{std::move(other.first_it), std::move(other.begin_it), std::move(other.end_it)}
142 constexpr reference operator*() const
144 noexcept(noexcept(*
std::declval<underlying_iterator_type>()))
146 return {*first_it, *second_it};
152 constexpr reference operator[](
size_t const index)
153 noexcept(noexcept(std::declval<iterator_type &>().from_index(1)))
155 requires
std::RandomAccessIterator<underlying_iterator_type>
166 constexpr iterator_type & operator++()
168 noexcept(noexcept(++
std::declval<underlying_iterator_type &>()))
170 if (++second_it == end_it)
173 second_it = first_it;
180 constexpr iterator_type operator++(
int )
181 noexcept(noexcept(std::declval<underlying_iterator_type &>()++))
183 iterator_type tmp{*
this};
189 constexpr iterator_type & operator--()
190 noexcept(noexcept(--
std::declval<underlying_iterator_type &>()))
192 requires
std::BidirectionalIterator<underlying_iterator_type>
195 if (--second_it == first_it)
205 constexpr iterator_type operator--(
int )
206 noexcept(noexcept(std::declval<underlying_iterator_type &>()--))
208 requires
std::BidirectionalIterator<underlying_iterator_type>
211 iterator_type tmp{*
this};
218 constexpr iterator_type & operator+=(difference_type
const offset)
219 noexcept(noexcept(std::declval<iterator_type &>().from_index(1)))
221 requires
std::RandomAccessIterator<underlying_iterator_type>
224 from_index(to_index() + offset);
230 constexpr iterator_type operator+(difference_type
const offset)
231 noexcept(noexcept(std::declval<iterator_type &>() += 1))
233 requires
std::RandomAccessIterator<underlying_iterator_type>
236 iterator_type tmp{*
this};
237 return (tmp += offset);
242 constexpr
friend iterator_type operator+(difference_type
const offset, iterator_type iter)
243 noexcept(noexcept(
std::declval<iterator_type<range_type> &>().from_index(1)))
245 requires
std::RandomAccessIterator<underlying_iterator_type>
248 iter.from_index(iter.to_index() + offset);
254 constexpr iterator_type & operator-=(difference_type
const offset)
255 noexcept(noexcept(std::declval<iterator_type &>().from_index(1)))
257 requires
std::RandomAccessIterator<underlying_iterator_type>
260 from_index(to_index() - offset);
266 constexpr iterator_type operator-(difference_type
const offset)
267 noexcept(noexcept(std::declval<iterator_type &>() -= 1))
269 requires
std::RandomAccessIterator<underlying_iterator_type>
272 iterator_type tmp{*
this};
273 return (tmp -= offset);
278 template <
typename other_range_type>
283 constexpr difference_type operator-(iterator_type<other_range_type>
const & rhs)
const 284 noexcept(noexcept(std::declval<iterator_type &>().to_index()))
286 return static_cast<difference_type
>(to_index() - rhs.to_index());
300 template <
typename other_range_type>
305 constexpr
bool operator==(iterator_type<other_range_type>
const & rhs)
const 306 noexcept(noexcept(std::declval<underlying_iterator_type &>() == std::declval<underlying_iterator_type &>()))
308 return std::tie(first_it, second_it) ==
std::tie(rhs.first_it, rhs.second_it);
312 template <
typename other_range_type>
317 constexpr
bool operator!=(iterator_type<other_range_type>
const & rhs)
const 318 noexcept(noexcept(std::declval<underlying_iterator_type &>() != std::declval<underlying_iterator_type &>()))
320 return !(*
this == rhs);
324 template <
typename other_range_type>
330 constexpr
bool operator<(iterator_type<other_range_type>
const & rhs)
const 331 noexcept(noexcept(std::declval<underlying_iterator_type &>() < std::declval<underlying_iterator_type &>()))
333 return std::tie(first_it, second_it) <
std::tie(rhs.first_it, rhs.second_it);
337 template <
typename other_range_type>
343 constexpr
bool operator>(iterator_type<other_range_type>
const & rhs)
const 344 noexcept(noexcept(std::declval<underlying_iterator_type &>() > std::declval<underlying_iterator_type &>()))
347 return std::tie(first_it, second_it) >
std::tie(rhs.first_it, rhs.second_it);
351 template <
typename other_range_type>
357 constexpr
bool operator<=(iterator_type<other_range_type>
const & rhs)
const 358 noexcept(noexcept(std::declval<underlying_iterator_type &>() <= std::declval<underlying_iterator_type &>()))
360 return std::tie(first_it, second_it) <=
std::tie(rhs.first_it, rhs.second_it);
364 template <
typename other_range_type>
370 constexpr
bool operator>=(iterator_type<other_range_type>
const & rhs)
const 371 noexcept(noexcept(std::declval<underlying_iterator_type &>() >= std::declval<underlying_iterator_type &>()))
373 return std::tie(first_it, second_it) >=
std::tie(rhs.first_it, rhs.second_it);
391 constexpr
size_t to_index() const
392 noexcept(noexcept(
std::declval<underlying_iterator_type &>() -
std::declval<underlying_iterator_type &>()))
394 requires
std::RandomAccessIterator<underlying_iterator_type>
397 size_t src_size = end_it - begin_it;
398 size_t index_i = first_it - begin_it;
399 size_t index_j = second_it - begin_it;
400 return (src_size * (src_size - 1)/2) - (src_size - index_i) * ((src_size - index_i) - 1)/2 +
401 index_j - index_i - 1;
408 constexpr
void from_index(
size_t const index)
409 noexcept(noexcept(std::declval<underlying_iterator_type &>() - std::declval<underlying_iterator_type &>()) &&
410 noexcept(std::declval<underlying_iterator_type &>() + 1))
412 requires
std::RandomAccessIterator<underlying_iterator_type>
415 size_t src_size = end_it - begin_it;
416 size_t index_i = src_size - 2 -
418 size_t index_j = index + index_i + 1 - src_size * (src_size - 1)/2 + (src_size - index_i) *
419 ((src_size - index_i) - 1)/2;
420 first_it = begin_it + index_i;
421 second_it = begin_it + index_j;
425 underlying_iterator_type first_it{};
427 underlying_iterator_type second_it{};
429 underlying_iterator_type begin_it{};
431 underlying_iterator_type end_it{};
440 using iterator = iterator_type<underlying_range_type>;
443 using const_iterator = transformation_trait_or_t<std::type_identity<iterator_type<underlying_range_type const>>,
446 using reference =
typename iterator::reference;
448 using const_reference = reference;
450 using value_type =
typename iterator::value_type;
452 using size_type = detail::transformation_trait_or_t<seqan3::size_type<underlying_range_type>,
void>;
454 using difference_type = difference_type_t<iterator>;
460 constexpr pairwise_combine_view() =
default;
463 constexpr pairwise_combine_view(pairwise_combine_view
const &) =
default;
465 constexpr pairwise_combine_view(pairwise_combine_view &&) =
default;
467 constexpr pairwise_combine_view & operator=(pairwise_combine_view
const &) =
default;
469 constexpr pairwise_combine_view & operator=(pairwise_combine_view &&) =
default;
471 ~pairwise_combine_view() =
default;
489 explicit constexpr pairwise_combine_view(underlying_range_type range) : u_range{std::move(range)}
511 auto tmp_it = back_iterator;
514 back_iterator = tmp_it;
540 template <
typename other_range_t>
549 explicit constexpr pairwise_combine_view(other_range_t && range) :
569 constexpr iterator
begin() noexcept
575 constexpr const_iterator
begin() const noexcept
577 requires ConstIterableRange<underlying_range_type>
584 constexpr const_iterator
cbegin() const noexcept
586 requires ConstIterableRange<underlying_range_type>
605 constexpr iterator
end() noexcept
611 constexpr const_iterator
end() const noexcept
613 requires ConstIterableRange<underlying_range_type>
620 constexpr const_iterator
cend() const noexcept
622 requires ConstIterableRange<underlying_range_type>
632 constexpr size_type
size() const noexcept
635 requires
std::
ranges::SizedRange<underlying_range_type>
645 underlying_range_type u_range{};
654 template <std::ranges::ViewableRange other_range_t>
656 pairwise_combine_view(other_range_t && range) ->
657 pairwise_combine_view<std::ranges::all_view<other_range_t>>;
731 inline constexpr
auto pairwise_combine = detail::adaptor_for_view_without_args<detail::pairwise_combine_view>{};
::ranges::cbegin cbegin
Alias for ranges::cbegin. Returns an iterator to the beginning of a range.
Definition: ranges:209
Specifies the requirements of a Range type that is either a std::ranges::View or an lvalue-reference...
::ranges::prev prev
Alias for ranges::prev. Returns the nth predecessor of the given iterator.
Definition: iterator:326
Specifies requirements of a Range type for which begin and end return objects of the same type...
constexpr auto pairwise_combine
A view adaptor that generates all pairwise combinations of the elements of the underlying range...
Definition: pairwise_combine.hpp:731
SeqAn specific customisations in the standard namespace.
constexpr auto all
A view adaptor that behaves like std::view:all, but type erases contiguous ranges.
Definition: view_all.hpp:160
::ranges::size size
Alias for ranges::size. Obtains the size of a range whose size can be calculated in constant time...
Definition: ranges:189
::ranges::view_interface< urng_t > view_interface
Alias for ranges::view_interface.
Definition: ranges:220
Requires std::EqualityComparable and all remaing comparison operators (<, <=, >, >=).
Specifies the requirements of a Range type that knows its size in constant time with the size functio...
Specifies requirements of a Range type for which begin returns a type that models std::BidirectionalI...
Additional non-standard concepts for ranges.
Auxiliary header for the view submodule .
::ranges::iterator_t iterator_t
Alias for ranges::iterator_t. Obtains the iterator type of a range.
Definition: ranges:204
Adaptations of concepts from the Ranges TS.
::ranges::begin begin
Alias for ranges::begin. Returns an iterator to the beginning of a range.
Definition: ranges:174
::ranges::advance advance
Alias for ranges::advance. Advances the iterator by the given distance.
Definition: iterator:316
The SeqAn3 namespace for views.
Definition: aligned_sequence_concept.hpp:35
The concept RandomAccessIterator refines std::BidirectionalIterator by adding support for constant ti...
The std::Constructible concept specifies that a variable of type T can be initialized with the given ...
Requires std::detail::WeaklyEqualityComparableWitht<t1,t2>, but also that t1 and t2, as well as their common_reference_t satisfy std::EqualityComparable.
::ranges::empty empty
Alias for ranges::empty. Checks whether a range is empty.
Definition: ranges:194
Specifies requirements of a Range type for which begin returns a type that models std::ForwardIterato...
::ranges::cend cend
Alias for ranges::cend. Returns an iterator to the end of a range.
Definition: ranges:214
The concept std::Same<T, U> is satisfied if and only if T and U denote the same type.
::ranges::end end
Alias for ranges::end. Returns an iterator to the end of a range.
Definition: ranges:179