23 Iterators library [iterators]

23.3 Iterator requirements [iterator.requirements]

23.3.7 Common algorithm requirements [alg.req]

23.3.7.1 General [alg.req.general]

There are several additional iterator concepts that are commonly applied to families of algorithms.
These group together iterator requirements of algorithm families.
There are three relational concepts that specify how element values are transferred between Readable and Writable types: IndirectlyMovable, IndirectlyCopyable, and IndirectlySwappable.
There are three relational concepts for rearrangements: Permutable, Mergeable, and Sortable.
There is one relational concept for comparing values from different sequences: IndirectlyComparable.
[Note
:
The ranges::less function object type used in the concepts below imposes constraints on the concepts' arguments in addition to those that appear in the concepts' bodies ([range.cmp]).
end note
]

23.3.7.2 Concept IndirectlyMovable [alg.req.ind.move]

The IndirectlyMovable concept specifies the relationship between a Readable type and a Writable type between which values may be moved.
template<class In, class Out>
  concept IndirectlyMovable =
    Readable<In> &&
    Writable<Out, iter_rvalue_reference_t<In>>;
The IndirectlyMovableStorable concept augments IndirectlyMovable with additional requirements enabling the transfer to be performed through an intermediate object of the Readable type's value type.
template<class In, class Out>
  concept IndirectlyMovableStorable =
    IndirectlyMovable<In, Out> &&
    Writable<Out, iter_value_t<In>> &&
    Movable<iter_value_t<In>> &&
    Constructible<iter_value_t<In>, iter_rvalue_reference_t<In>> &&
    Assignable<iter_value_t<In>&, iter_rvalue_reference_t<In>>;
Let i be a dereferenceable value of type In.
In and Out model IndirectlyMovableStorable<In, Out> only if after the initialization of the object obj in
iter_value_t<In> obj(ranges::iter_move(i));
obj is equal to the value previously denoted by *i.
If iter_­rvalue_­reference_­t<In> is an rvalue reference type, the resulting state of the value denoted by *i is valid but unspecified ([lib.types.movedfrom]).

23.3.7.3 Concept IndirectlyCopyable [alg.req.ind.copy]

The IndirectlyCopyable concept specifies the relationship between a Readable type and a Writable type between which values may be copied.
template<class In, class Out>
  concept IndirectlyCopyable =
    Readable<In> &&
    Writable<Out, iter_reference_t<In>>;
The IndirectlyCopyableStorable concept augments IndirectlyCopyable with additional requirements enabling the transfer to be performed through an intermediate object of the Readable type's value type.
It also requires the capability to make copies of values.
template<class In, class Out>
  concept IndirectlyCopyableStorable =
    IndirectlyCopyable<In, Out> &&
    Writable<Out, const iter_value_t<In>&> &&
    Copyable<iter_value_t<In>> &&
    Constructible<iter_value_t<In>, iter_reference_t<In>> &&
    Assignable<iter_value_t<In>&, iter_reference_t<In>>;
Let i be a dereferenceable value of type In.
In and Out model IndirectlyCopyableStorable<In, Out> only if after the initialization of the object obj in
iter_value_t<In> obj(*i);
obj is equal to the value previously denoted by *i.
If iter_­reference_­t<In> is an rvalue reference type, the resulting state of the value denoted by *i is valid but unspecified ([lib.types.movedfrom]).

23.3.7.4 Concept IndirectlySwappable [alg.req.ind.swap]

The IndirectlySwappable concept specifies a swappable relationship between the values referenced by two Readable types.
template<class I1, class I2 = I1>
  concept IndirectlySwappable =
    Readable<I1> && Readable<I2> &&
    requires(I1& i1, I2& i2) {
      ranges::iter_swap(i1, i1);
      ranges::iter_swap(i2, i2);
      ranges::iter_swap(i1, i2);
      ranges::iter_swap(i2, i1);
    };

23.3.7.5 Concept IndirectlyComparable [alg.req.ind.cmp]

The IndirectlyComparable concept specifies the common requirements of algorithms that compare values from two different sequences.
template<class I1, class I2, class R, class P1 = identity,
         class P2 = identity>
  concept IndirectlyComparable =
    IndirectRelation<R, projected<I1, P1>, projected<I2, P2>>;

23.3.7.6 Concept Permutable [alg.req.permutable]

The Permutable concept specifies the common requirements of algorithms that reorder elements in place by moving or swapping them.
template<class I>
  concept Permutable =
    ForwardIterator<I> &&
    IndirectlyMovableStorable<I, I> &&
    IndirectlySwappable<I, I>;

23.3.7.7 Concept Mergeable [alg.req.mergeable]

The Mergeable concept specifies the requirements of algorithms that merge sorted sequences into an output sequence by copying elements.
template<class I1, class I2, class Out, class R = ranges::less,
         class P1 = identity, class P2 = identity>
  concept Mergeable =
    InputIterator<I1> &&
    InputIterator<I2> &&
    WeaklyIncrementable<Out> &&
    IndirectlyCopyable<I1, Out> &&
    IndirectlyCopyable<I2, Out> &&
    IndirectStrictWeakOrder<R, projected<I1, P1>, projected<I2, P2>>;

23.3.7.8 Concept Sortable [alg.req.sortable]

The Sortable concept specifies the common requirements of algorithms that permute sequences into ordered sequences (e.g., sort).
template<class I, class R = ranges::less, class P = identity>
  concept Sortable =
    Permutable<I> &&
    IndirectStrictWeakOrder<R, projected<I, P>>;