Files
2025-10-25 03:02:53 +03:00

13 KiB
Raw Permalink Blame History

[range.iter.ops]

24 Iterators library [iterators]

24.4 Iterator primitives [iterator.primitives]

24.4.4 Range iterator operations [range.iter.ops]

24.4.4.1 General [range.iter.ops.general]

1

#

The library includes the function templatesranges::advance, ranges::distance,ranges::next, and ranges::prev to manipulate iterators.

These operations adapt to the set of operators provided by each iterator category to provide the most efficient implementation possible for a concrete iterator type.

[Example 1:

ranges::advance uses the + operator to move arandom_access_iterator forward n steps in constant time.

For an iterator type that does not model random_access_iterator,ranges::advance instead performs n individual increments with the ++ operator.

— end example]

2

#

The entities defined in [range.iter.ops] are algorithm function objects ([alg.func.obj]).

24.4.4.2 ranges::advance [range.iter.op.advance]

🔗

template<[input_or_output_iterator](iterator.concept.iterator#concept:input_or_output_iterator "24.3.4.6Concept input_­or_­output_­iterator[iterator.concept.iterator]") I> constexpr void ranges::advance(I& i, iter_difference_t<I> n);

1

#

Preconditions: If I does not model bidirectional_iterator,n is not negative.

2

#

Effects:

🔗

template<[input_or_output_iterator](iterator.concept.iterator#concept:input_or_output_iterator "24.3.4.6Concept input_­or_­output_­iterator[iterator.concept.iterator]") I, [sentinel_for](iterator.concept.sentinel#concept:sentinel_for "24.3.4.7Concept sentinel_­for[iterator.concept.sentinel]")<I> S> constexpr void ranges::advance(I& i, S bound);

3

#

Preconditions: Either assignable_from<I&, S> || sized_sentinel_for<S, I> is modeled, or [i, bound) denotes a range.

4

#

Effects:

  • (4.1)

    If I and S model assignable_from<I&, S>, equivalent to i = std::move(bound).

  • (4.2)

    Otherwise, if S and I model sized_sentinel_for<S, I>, equivalent to ranges::advance(i, bound - i).

  • (4.3)

    Otherwise, while bool(i != bound) is true, increments i.

🔗

template<[input_or_output_iterator](iterator.concept.iterator#concept:input_or_output_iterator "24.3.4.6Concept input_­or_­output_­iterator[iterator.concept.iterator]") I, [sentinel_for](iterator.concept.sentinel#concept:sentinel_for "24.3.4.7Concept sentinel_­for[iterator.concept.sentinel]")<I> S> constexpr iter_difference_t<I> ranges::advance(I& i, iter_difference_t<I> n, S bound);

5

#

Preconditions: If n > 0, [i, bound) denotes a range.

If n == 0, [i, bound) or [bound, i) denotes a range.

If n < 0, [bound, i) denotes a range,I models bidirectional_iterator, andI and S model same_as<I, S>.

6

#

Effects:

  • (6.1)

    If S and I model sized_sentinel_for<S, I>:

    • (6.1.1)

      If |n| ≥ |bound - i|, equivalent to ranges::advance(i, bound).

    • (6.1.2)

      Otherwise, equivalent to ranges::advance(i, n).

  • (6.2)

    Otherwise,

    • (6.2.1)

      if n is non-negative, while bool(i != bound) is true, increments i but at most n times.

    • (6.2.2)

      Otherwise, while bool(i != bound) is true, decrements i but at most -n times.

7

#

Returns: n - M, where M is the difference between the ending and starting positions of i.

24.4.4.3 ranges::distance [range.iter.op.distance]

🔗

template<class I, [sentinel_for](iterator.concept.sentinel#concept:sentinel_for "24.3.4.7Concept sentinel_­for[iterator.concept.sentinel]")<I> S> requires (![sized_sentinel_for](iterator.concept.sizedsentinel#concept:sized_sentinel_for "24.3.4.8Concept sized_­sentinel_­for[iterator.concept.sizedsentinel]")<S, I>) constexpr iter_difference_t<I> ranges::distance(I first, S last);

1

#

Preconditions: [first, last) denotes a range.

2

#

Effects: Increments first until last is reached and returns the number of increments.

🔗

template<class I, [sized_sentinel_for](iterator.concept.sizedsentinel#concept:sized_sentinel_for "24.3.4.8Concept sized_­sentinel_­for[iterator.concept.sizedsentinel]")<decay_t<I>> S> constexpr iter_difference_t<decay_t<I>> ranges::distance(I&& first, S last);

3

#

Effects: Equivalent to:if constexpr (!is_array_v<remove_reference_t>)return last - first;elsereturn last - static_cast<decay_t>(first);

🔗

template<[range](range.range#concept:range "25.4.2Ranges[range.range]") R> constexpr range_difference_t<R> ranges::distance(R&& r);

4

#

Effects: If R models sized_range, equivalent to:return static_cast<range_difference_t>(ranges::size(r)); // [range.prim.size]

Otherwise, equivalent to:return ranges::distance(ranges::begin(r), ranges::end(r)); // [range.access]

24.4.4.4 ranges::next [range.iter.op.next]

🔗

template<[input_or_output_iterator](iterator.concept.iterator#concept:input_or_output_iterator "24.3.4.6Concept input_­or_­output_­iterator[iterator.concept.iterator]") I> constexpr I ranges::next(I x);

1

#

Effects: Equivalent to: ++x; return x;

🔗

template<[input_or_output_iterator](iterator.concept.iterator#concept:input_or_output_iterator "24.3.4.6Concept input_­or_­output_­iterator[iterator.concept.iterator]") I> constexpr I ranges::next(I x, iter_difference_t<I> n);

2

#

Effects: Equivalent to: ranges::advance(x, n); return x;

🔗

template<[input_or_output_iterator](iterator.concept.iterator#concept:input_or_output_iterator "24.3.4.6Concept input_­or_­output_­iterator[iterator.concept.iterator]") I, [sentinel_for](iterator.concept.sentinel#concept:sentinel_for "24.3.4.7Concept sentinel_­for[iterator.concept.sentinel]")<I> S> constexpr I ranges::next(I x, S bound);

3

#

Effects: Equivalent to: ranges::advance(x, bound); return x;

🔗

template<[input_or_output_iterator](iterator.concept.iterator#concept:input_or_output_iterator "24.3.4.6Concept input_­or_­output_­iterator[iterator.concept.iterator]") I, [sentinel_for](iterator.concept.sentinel#concept:sentinel_for "24.3.4.7Concept sentinel_­for[iterator.concept.sentinel]")<I> S> constexpr I ranges::next(I x, iter_difference_t<I> n, S bound);

4

#

Effects: Equivalent to: ranges::advance(x, n, bound); return x;

24.4.4.5 ranges::prev [range.iter.op.prev]

🔗

template<[bidirectional_iterator](iterator.concept.bidir#concept:bidirectional_iterator "24.3.4.12Concept bidirectional_­iterator[iterator.concept.bidir]") I> constexpr I ranges::prev(I x);

1

#

Effects: Equivalent to: --x; return x;

🔗

template<[bidirectional_iterator](iterator.concept.bidir#concept:bidirectional_iterator "24.3.4.12Concept bidirectional_­iterator[iterator.concept.bidir]") I> constexpr I ranges::prev(I x, iter_difference_t<I> n);

2

#

Effects: Equivalent to: ranges::advance(x, -n); return x;

🔗

template<[bidirectional_iterator](iterator.concept.bidir#concept:bidirectional_iterator "24.3.4.12Concept bidirectional_­iterator[iterator.concept.bidir]") I> constexpr I ranges::prev(I x, iter_difference_t<I> n, I bound);

3

#

Effects: Equivalent to: ranges::advance(x, -n, bound); return x;