cpp/iterator

Iterators are a generalization of pointers that allow a C++ program to work with different data structures (for example, containers) in a uniform manner. The iterator library provides definitions for iterators, as well as iterator traits, adaptors, and utility functions.

Since iterators are an abstraction of pointers, their semantics are a generalization of most of the semantics of pointers in C++. This ensures that every function template that takes iterators works as well with regular pointers.

Iterator categories
There are kinds of iterators:, , , ,.

Instead of being defined by specific types, each category of iterator is defined by the operations that can be performed on it. This definition means that any type that supports the necessary operations can be used as an iterator -- for example, a pointer supports all of the operations required by, so a pointer can be used anywhere a is expected.

All of the iterator categories (except ) can be organized into a hierarchy, where more powerful iterator categories (e.g. ) support the operations of less powerful categories (e.g. ). If an iterator falls into one of these categories and also satisfies the requirements of, then it is called a mutable iterator and supports both input and output. Non-mutable iterators are called constant iterators.

Note: A type supporting the required operations in a row of the table above does not necessarily fall into the corresponding category, see the category page for the complete list of requirements.

Types and writability
An input iterator supports the expression, resulting in a value of some object type , called the value type of the iterator.

An output iterator has a non-empty set of types that are  to the iterator; for each such type, the expression  is valid where  is a value of type.

For every iterator type, there is a corresponding signed  type called the difference type of the iterator.

Dereferenceability and validity
Just as a regular pointer to an array guarantees that there is a pointer value pointing past the last element of the array, so for any iterator type there is an iterator value that points past the last element of a corresponding sequence. Such a value is called a past-the-end value.

Values of an iterator for which the expression  is defined are called dereferenceable. The standard library never assumes that past-the-end values are dereferenceable.

Iterators can also have singular values that are not associated with any sequence. Results of most expressions are undefined for singular values; the only exceptions are In these cases the singular value is overwritten the same way as any other value. Dereferenceable values are always non-singular.
 * the assignment of a non-singular value to an iterator that holds a singular value,
 * destroying an iterator that holds a singular value, and,
 * for iterators that meet the requirements, using a value-initialized iterator as the source of a copy  operation.

An invalid iterator is an iterator that may be singular.

Ranges
Most of the standard library’s algorithmic templates that operate on data structures have interfaces that use ranges.

{{rev|since=c++20| A range is either
 * a comparable range {{tt|[i, s)}}, an iterator {{c|i}} and a sentinel {{c|s}} that designate the beginning and end of the computation ({{c|i}} and {{c|s}} can have different types), or
 * a counted range {{tt|i + [0, n)}}, an iterator {{c|i}} and a count {{c|n}} that designate the beginning and the number of elements to which the computation is to be applied.

Comparable range
An iterator and a sentinel denoting a range are comparable. is empty if ; otherwise, refers to the elements in the data structure starting with the element pointed to by  and up to but not including the element, if any, pointed to by the first iterator  such that.

A sentinel is called reachable from an iterator  if and only if there is a finite sequence of applications of the expression  that makes.

If is reachable from,  denotes a valid range.

Counted range
A counted range is empty if ; otherwise,  refers to the  elements in the data structure starting with the element pointed to by  and up to but not including the element, if any, pointed to by the result of  applications of.

A counted range is valid if and only if }}
 * ; or
 * all of the following conditions are satisfied:
 * is positive,
 * is dereferenceable, and
 * is valid.

The result of the application of functions in the standard library to invalid ranges is undefined.

Iterator concepts
C++20 introduces a new system of iterators based on concepts that are different from C++17 iterators. While the basic taxonomy remains similar, the requirements for individual iterator categories are somewhat different.

Algorithm concepts and utilities
C++20 also provides a set of concepts and related utility templates designed to ease constraining common algorithm operations.

Range access
These non-member functions provide a generic interface for containers, plain arrays, and std.