std.range

This module defines the notion of a range. Ranges generalize the concept of arrays, lists, or anything that involves sequential access. This abstraction enables the same set of algorithms (see std.algorithm) to be used with a vast variety of different concrete types. For example, a linear search algorithm such as find works not just for arrays, but for linked-lists, input files, incoming network data, etc.

Guides:

There are many articles available that can bolster understanding ranges:

Submodules:

This module has two submodules:

The std.range.primitives submodule provides basic range functionality. It defines several templates for testing whether a given object is a range, what kind of range it is, and provides some common range operations.

The std.range.interfaces submodule provides object-based interfaces for working with ranges via runtime polymorphism.

The remainder of this module provides a rich set of range creation and composition templates that let you construct new ranges out of existing ranges:

Sortedness:

Ranges whose elements are sorted afford better efficiency with certain operations. For this, the assumeSorted function can be used to construct a SortedRange from a pre-sorted range. The sort function also conveniently returns a SortedRange. SortedRange objects provide some additional range operations that take advantage of the fact that the range is sorted.

Source: std/range/package.d

License

Boost License 1.0.

Authors

Andrei Alexandrescu, David Simcha, Jonathan M Davis, and Jack Stouffer. Credit

for some of the ideas in building this module goes to

Leonardo Maffi.

Types 30

private structChooseResult(Ranges...)
Fields
private size_t chosenI
Methods
private static auto ref actOnChosen(alias foo, ExtraArgs ...)(ref ChooseResult r, auto ref ExtraArgs extraArgs)
@property auto ref front()
void popFront()
Constructors
this(size_t chosen, return scope Ranges rs)
Nested Templates
front(T)
structTake(Range) if (isInputRange!(Unqual!Range) && //take _cannot_ test hasSlicing on infinite ranges, because hasSlicing uses //take for slicing infinite ranges. !((!isInfinite!(Unqual!Range) && hasSlicing!(Unqual!Range)) || is(Range T == Take!T)))

ditto

Fields
R sourceUser accessible in read and write
private size_t _maxAvailable
Methods
bool empty() @propertyRange primitives
@property auto ref front()ditto
void popFront()ditto
size_t maxLength() @property constAccess to maximal length of the range. Note: the actual length of the range depends on the underlying range. If it has fewer elements, it will stop before maxLength is reached.
structRepeat(T)

Create a range which repeats one value.

Parameters

valuethe _value to repeat
nthe number of times to repeat value

Returns

If n is not defined, an infinite random access range

with slicing.

If n is defined, a random access range with slicing.

Fields
Rebindable2!T _value
bool emptyditto
DollarToken.init opDollarditto
Methods
inout(T) front() @property inoutRange primitives
inout(T) back() @property inoutditto
void popFront()ditto
void popBack()ditto
@property auto save() inoutditto
inout(T) opIndex(size_t) inoutditto
auto opSlice(size_t i, size_t j)ditto
auto opSlice(size_t, DollarToken) inoutditto
Nested Templates
DollarToken
private structGenerator(Fun...)
Fields
(functionAttributes!fun & FunctionAttribute.ref_) ? true : false returnByRef_
false emptyRange primitives
structCycle(R) if (isForwardRange!R && !isInfinite!R)

Repeats the given forward range ad infinitum. If the original range is infinite (fact that would make Cycle the identity application), Cycle detects that and aliases itself to the range type itself. That works for non-forward ranges too. If the original range has random access, Cycle offers random access and also offers a constructor taking an initial position index. Cycle works with static arrays in addition to ranges, mostly for performance reasons.

Note

The input range must not be empty.

Tip: This is a great way to implement simple circular buffers.

structCycle(R) if (isStaticArray!R)

ditto

Fields
private ElementType * _ptr
private size_t _index
bool emptyditto
DollarToken.init opDollarditto
Methods
inout(ElementType) front() @property ref inout @safeditto
void popFront() @safeditto
inout(ElementType) opIndex(size_t n) ref inout @safeditto
inout(Cycle) save() @property inout @safeditto
auto opSlice(size_t i, size_t j) @safeditto
inout(typeof(this)) opSlice(size_t i, DollarToken) inout @safeditto
Constructors
this(ref R input, size_t index = 0)Range primitives
Nested Templates
DollarToken
private aliaslengthType(R) = typeof(R.init.length.init)
structZip(Ranges...) if (Ranges.length && allSatisfy!(isInputRange, Ranges))

Iterate several ranges in lockstep. The element type is a proxy tuple that allows accessing the current element in the nth range by using e[n].

zip is similar to lockstep, but lockstep doesn't bundle its elements and uses the opApply protocol. lockstep allows reference access to the elements in foreach iterations.

Parameters

spcontrols what zip will do if the ranges are different lengths
rangesthe ranges to zip together

Returns

At minimum, an input range. Zip offers the lowest range facilities

of all components, e.g. it offers random access iff all ranges offer random access, and also offers mutation and swapping if all ranges offer it. Due to this, Zip is extremely powerful because it allows manipulating several ranges in lockstep.

Throws

An Exception if all of the ranges are not the same length and

sp is set to StoppingPolicy.requireSameLength.

Limitations: The @nogc and nothrow attributes cannot be inferred for the Zip struct because StoppingPolicy can vary at runtime. This limitation is not shared by the anonymous range returned by the zip function when not given an explicit StoppingPolicy as an argument.

Fields
private R ranges
private StoppingPolicy stoppingPolicy
Methods
private .ElementType!(R[i]) tryGetInit(size_t i)()
ElementType front() @propertyReturns the current iterated element.
void popFront()Advances to the next element in all controlled ranges.
Constructors
this(R rs, StoppingPolicy s = StoppingPolicy.shortest)Builds an object. Usually this is invoked indirectly by using the zip function.

Dictates how iteration in a zip and lockstep should stop. By default stop at the end of the shortest of all ranges.

shortestStop when the shortest range is exhausted
longestStop when the longest range is exhausted
requireSameLengthRequire that all ranges are equal
structZipShortest(Flag!"allKnownSameLength" allKnownSameLength, Ranges...) if (Ranges.length && allSatisfy!(isInputRange, Ranges))
Fields
private Ranges ranges
private bool isBackWellDefined
Methods
ElementType front() @property
void popFront()
Constructors
this(Ranges rs)
private structLockstepMixin(Ranges...)
Fields
string name
string implName
string[] params
string[] emptyChecks
string[] dgArgs
string[] popFronts
string indexDef
string indexInc
Methods
string getAlias()
string getImpl()
Constructors
this(bool withIndex, bool reverse)
structLockstep(Ranges...) if (Ranges.length > 1 && allSatisfy!(isInputRange, Ranges))

Iterate multiple ranges in lockstep using a foreach loop. In contrast to

zip it allows reference access to its elements. If only a single

range is passed in, the Lockstep aliases itself away. If the ranges are of different lengths and s == StoppingPolicy.shortest stop after the shortest range is empty. If the ranges are of different lengths and s == StoppingPolicy.requireSameLength, throw an exception. s may not be StoppingPolicy.longest, and passing this will throw an exception.

Iterating over Lockstep in reverse and with an index is only possible when s == StoppingPolicy.requireSameLength, in order to preserve indexes. If an attempt is made at iterating in reverse when s == StoppingPolicy.shortest, an exception will be thrown.

By default StoppingPolicy is set to StoppingPolicy.shortest.

See Also

zip

lockstep is similar to zip, but zip bundles its elements and returns a range. lockstep also supports reference access. Use zip if you want to pass the result to a range function.

Fields
private Ranges ranges
private StoppingPolicy stoppingPolicy
private LockstepMixin!Ranges(withIndex: false, reverse: false) lockstepMixinFF
private LockstepMixin!Ranges(withIndex: true, reverse: false) lockstepMixinTF
Constructors
this(Ranges ranges, StoppingPolicy sp = StoppingPolicy.shortest)
structRecurrence(alias fun, StateType, size_t stateSize)

Creates a mathematical sequence given the initial values and a recurrence function that computes the next value from the existing values. The sequence comes in the form of an infinite forward range. The type Recurrence itself is seldom used directly; most often, recurrences are obtained by calling the function recurrence.

When calling recurrence, the function that computes the next value is specified as a template argument, and the initial values in the recurrence are passed as regular arguments. For example, in a Fibonacci sequence, there are two initial values (and therefore a state size of 2) because computing the next Fibonacci value needs the past two values.

The signature of this function should be: ---- auto fun(R)(R state, size_t n) ---- where n will be the index of the current value, and state will be an opaque state vector that can be indexed with array-indexing notation state[i], where valid values of i range from (n - 1) to

(n - State.length).

If the function is passed in string form, the state has name "a" and the zero-based index in the recurrence has name "n". The given string must return the desired value for a[n] given a[n - 1], a[n - 2], a[n - 3],..., a[n - stateSize]. The state size is dictated by the number of arguments passed to the call to recurrence. The Recurrence struct itself takes care of managing the recurrence's state and shifting it appropriately.

Fields
StateType[stateSize] _state
size_t _n
bool empty
Methods
void popFront()
StateType front() @property
typeof(this) save() @property
Constructors
this(StateType[stateSize] initial)
structSequence(alias fun, State)

Sequence is similar to Recurrence except that iteration is presented in the so-called closed form. This means that the nth element in the series is computable directly from the initial values and n itself. This implies that the interface offered by Sequence is a random-access range, as opposed to the regular Recurrence, which only offers forward iteration.

The state of the sequence is stored as a Tuple so it can be heterogeneous.

Fields
State _state
size_t _n
DollarToken() opDollar
bool empty
Methods
ElementType front() @property
void popFront()
auto opSlice(size_t lower, size_t upper)
auto opSlice(size_t lower, DollarToken)
Sequence save() @property
Constructors
this(State initial, size_t n = 0)
Nested Templates
DollarToken

Options for the FrontTransversal and Transversal ranges (below).

assumeJaggedWhen transversed, the elements of a range of ranges are assumed to have different lengths (e.g. a jagged array).
enforceNotJaggedThe transversal enforces that the elements of a range of ranges have all the same length (e.g. an array of arrays, all having the same length). Checking is done once upon construction of the transv...
assumeNotJaggedThe transversal assumes, without verifying, that the elements of a range of ranges have all the same length. This option is useful if checking was already done from the outside of the range.
structFrontTransversal(Ror, TransverseOptions opt = TransverseOptions.assumeJagged)

Given a range of ranges, iterate transversally through the first elements of each of the enclosed ranges.

Fields
RangeOfRanges _input
Methods
private void prime()
@property auto ref front()Ditto
void popFront()Ditto
auto opSlice()
Constructors
this(RangeOfRanges input)Construction from an input.
structTransversal(Ror, TransverseOptions opt = TransverseOptions.assumeJagged)

Given a range of ranges, iterate transversally through the nth element of each of the enclosed ranges. This function is similar to unzip in other languages.

Parameters

optControls the assumptions the function makes about the lengths of the ranges
rrAn input range of random access ranges

Returns

At minimum, an input range. Range primitives such as bidirectionality

and random access are given if the element type of rr provides them.

Fields
RangeOfRanges _input
size_t _n
Methods
private void prime()
@property auto ref front()Ditto
void popFront()Ditto
auto opSlice()
Constructors
this(RangeOfRanges input, size_t n)Construction from an input and an index.
structTransposed(RangeOfRanges, TransverseOptions opt = TransverseOptions.assumeJagged) if (isForwardRange!RangeOfRanges && isInputRange!(ElementType!RangeOfRanges) && hasAssignableElements!RangeOfRanges)
Fields
RangeOfRanges _input
Methods
@property auto front()
void popFront()
bool empty() @property
auto opSlice()
Constructors
this(RangeOfRanges input)
structIndexed(Source, Indices) if (isRandomAccessRange!Source && isInputRange!Indices && is(typeof(Source.init[ElementType!(Indices).init])))

This struct takes two ranges, source and indices, and creates a view of source as if its elements were reordered according to indices. indices may include only a subset of the elements of source and may also repeat elements.

Source must be a random access range. The returned range will be bidirectional or random-access if Indices is bidirectional or random-access, respectively.

Fields
Source _source
Indices _indices
Methods
@property auto ref front()Range primitives
void popFront()Ditto
Source source() @propertyReturns the source range.
Indices indices() @propertyReturns the indices range.
Constructors
this(Source source, Indices indices)
structChunks(Source) if (isInputRange!Source)

This range iterates over fixed-sized chunks of size chunkSize of a source range. Source must be an input range. chunkSize must be greater than zero.

If !isInfinite!Source and source.walkLength is not evenly divisible by chunkSize, the back element of this range will contain fewer than chunkSize elements.

If Source is a forward range, the resulting range will be forward ranges as well. Otherwise, the resulting chunks will be input ranges consuming the same input: iterating over front will shrink the chunk such that subsequent invocations of front will no longer return the full chunk, and calling popFront on the outer range will invalidate any lingering references to previous values of front.

Parameters

sourceRange from which the chunks will be selected
chunkSizeChunk size

See Also

slide

Returns

Range of chunks.
structEvenChunks(Source) if (isForwardRange!Source && hasLength!Source)

This range splits a source range into chunkCount chunks of approximately equal length. Source must be a forward range with known length.

Unlike chunks, evenChunks takes a chunk count (not size). The returned range will contain zero or more source.length / chunkCount + 1 elements followed by source.length / chunkCount elements. If source.length < chunkCount, some chunks will be empty.

chunkCount must not be zero, unless source is also empty.

Fields
Source _source
size_t _chunkCount
Methods
@property auto front()Forward range primitives. Always present.
void popFront()Ditto
bool empty() @propertyDitto
typeof(this) save() @propertyDitto
size_t length() @property constLength
size_t _chunkPos(size_t i)
Constructors
this(Source source, size_t chunkCount)Standard constructor
private structSlides(Flag!"withPartial" withPartial = Yes.withPartial, Source) if (isForwardRange!Source)
Fields
Source source
size_t windowSize
size_t stepSize
bool _empty
Methods
@property auto front()Forward range primitives. Always present.
void popFront()Ditto
typeof(this) save() @propertyDitto
Constructors
this(Source source, size_t windowSize, size_t stepSize)Standard constructor
private structOnlyResult(Values...) if (Values.length > 1)
Fields
private Values.length arity
private allSatisfy!( ApplyRight!(isAssignable, CommonType!Values), Values ) canAssignElements
private size_t frontIndex
private size_t backIndex
Methods
bool empty() @property
CommonType!Values front() @property
void popFront()
CommonType!Values back() @property
void popBack()
OnlyResult save() @property
size_t length() const @property
CommonType!Values opIndex(size_t idx) @trusted
OnlyResult opSlice(size_t from, size_t to)
Constructors
this(return scope ref Values values)
private structOnlyResult(T)
Fields
private Unqual!T _value
private bool _empty
Methods
T front() @property
T back() @property
bool empty() @property const
size_t length() @property const
@property auto save()
void popFront()
void popBack()
T opIndex(size_t i)
OnlyResult opSlice(size_t from, size_t to)
private T fetchFront() @trusted
Constructors
this(return scope auto ref T value)

Policy used with the searching primitives lowerBound, upperBound, and equalRange of SortedRange below.

linearSearches in a linear fashion.
trotSearches with a step that is grows linearly (1, 2, 3,...) leading to a quadratic search schedule (indexes tried are 0, 1, 3, 6, 10, 15, 21, 28,...) Once the search overshoots its target, the remain...
gallopPerforms a https://en.wikipedia.org/wiki/Exponential_search, i.e. searches with a step that doubles every time, (1, 2, 4, 8, ...) leading to an exponential search schedule (indexes tried are 0, 1,...
binarySearchSearches using a classic interval halving policy. The search starts in the middle of the range, and each search step cuts the range in half. This policy finds a value in log(n) time but is less cac...
trotBackwardsSimilar to `trot` but starts backwards. Use it when confident that the value is around the end of the range.
gallopBackwardsSimilar to `gallop` but starts backwards. Use it when confident that the value is around the end of the range.

Options for SortedRange ranges (below).

assumeSortedAssume, that the range is sorted without checking.
checkStrictlyAll elements of the range are checked to be sorted. The check is performed in O(n) time.
checkRoughlySome elements of the range are checked to be sorted. For ranges with random order, this will almost surely detect, that it is not sorted. For almost sorted ranges it's more likely to fail. The chec...
structSortedRange(Range, alias pred = "a < b", SortedRangeOptions opt = SortedRangeOptions.assumeSorted) if (isInputRange!Range && !isInstanceOf!(SortedRange, Range))

Represents a sorted range. In addition to the regular range primitives, supports additional operations that take advantage of the ordering, such as merge and binary search. To obtain a SortedRange from an unsorted range r, use

sort which sorts r in place and returns the

corresponding SortedRange. To construct a SortedRange from a range r that is known to be already sorted, use assumeSorted.

Parameters

Fields
private Range _input
Methods
private bool geq(L, R)(L lhs, R rhs)
private bool gt(L, R)(L lhs, R rhs)
bool empty() @propertyRange primitives.
@property auto ref front()Ditto
void popFront()Ditto
auto release() return scopeReleases the controlled range and returns it.
private size_t getTransitionIndex(SearchPolicy sp, alias test, V)(V v) if (sp == SearchPolicy.binarySearch && isRandomAccessRange!Range && hasLength!Range)
private size_t getTransitionIndex(SearchPolicy sp, alias test, V)(V v) if ((sp == SearchPolicy.trot || sp == SearchPolicy.gallop) && isRandomAccessRange!Range)
private size_t getTransitionIndex(SearchPolicy sp, alias test, V)(V v) if ((sp == SearchPolicy.trotBackwards || sp == SearchPolicy.gallopBackwards) && isRandomAccessRange!Range)
auto lowerBound(SearchPolicy sp = SearchPolicy.binarySearch, V)(V value) if (isTwoWayCompatible!(predFun, ElementType!Range, V) && hasSlicing!Range)This function uses a search with policy `sp` to find the largest left subrange on which pred(x) is `true` for all `x` (e.g., if `pred` is "less than", returns the portion of the range with elements...
auto upperBound(SearchPolicy sp = SearchPolicy.binarySearch, V)(V value) if (isTwoWayCompatible!(predFun, ElementType!Range, V))This function searches with policy `sp` to find the largest right subrange on which pred(value) is `true` for all `x` (e.g., if `pred` is "less than", returns the portion of the range with elements...
auto equalRange(V)(V value) if (isTwoWayCompatible!(predFun, ElementType!Range, V) && isRandomAccessRange!Range)Returns the subrange containing all elements `e` for which both pred(e) and pred(value) evaluate to `false` (e.g., if `pred` is "less than", returns the portion of the range with elements equal to ...
auto trisect(V)(V value) if (isTwoWayCompatible!(predFun, ElementType!Range, V) && isRandomAccessRange!Range && hasLength!Range)Returns a tuple `r` such that `r[0]` is the same as the result of `lowerBound(value)`, `r[1]` is the same as the result of equalRange(value), and `r[2]` is the same as the result of upperBound(valu...
bool contains(V)(V value) if (isRandomAccessRange!Range)Returns `true` if and only if `value` can be found in range, which is assumed to be sorted. Performs log(r.length) evaluations of `pred`.
bool opBinaryRight(string op, V)(V value) if (op == "in" && isRandomAccessRange!Range)Like `contains`, but the value is specified before the range.
auto groupBy()()Returns a range of subranges of elements that are equivalent according to the sorting relation.
Constructors
this(Range input)
structRefRange(R) if (isInputRange!R)

Wrapper which effectively makes it possible to pass a range by reference. Both the original range and the RefRange will always have the exact same elements. Any operation done on one will affect the other. So, for instance, if it's passed to a function which would implicitly copy the original range if it were passed to it, the original range is not copied but is consumed as if it were a reference type.

Note

save works as normal and operates on a new range, so if

save is ever called on the RefRange, then no operations on the saved range will affect the original.

Parameters

rangethe range to construct the RefRange from

Returns

A RefRange. If the given range is a class type

(and thus is already a reference type), then the original range is returned rather than a RefRange.

Fields
R * _range
Methods
auto opAssign(RefRange rhs)This does not assign the pointer of `rhs` to this `RefRange`. Rather it assigns the range pointed to by `rhs` to the range pointed to by this `RefRange`. This is because any operation on a `RefRang...
void opAssign(typeof(null) rhs)
inout(R *) ptr() @property @safe inout pure nothrowA pointer to the wrapped range.
void popFront()
Constructors
this(R * range)
private structBitwise(R) if (isInputRange!R && isIntegral!(ElementType!R))
Fields
R parent
ElemType.sizeof * 8 bitsNum
size_t maskPos
Methods
bool front()
void popFront()
auto mask(size_t maskPos)
Constructors
this(auto ref R range)
structNullSink

An OutputRange that discards the data it receives.

Methods
void put(E)(scope const E) pure @safe @nogc nothrow

Functions 58

fnauto retro(Range)(Range r) if (isBidirectionalRange!(Unqual!Range))Iterates a bidirectional range backwards. The original range can be accessed by using the `source` property. Applying retro twice to the same range yields the original range.
fnauto stride(Range)(Range r, size_t n) if (isInputRange!(Unqual!Range))Iterates range `r` with stride `n`. If the range is a random-access range, moves by indexing into the range; otherwise, moves by successive calls to `popFront`. Applying stride twice to the same ra...
fnauto chain(Ranges...)(Ranges rs) if (Ranges.length > 0 && allSatisfy!(isInputRange, staticMap!(Unqual, Ranges)) && !is(CommonType!(staticMap!(ElementType, staticMap!(Unqual, Ranges))) == void))Spans multiple ranges in sequence. The function `chain` takes any number of ranges and returns a Chain!(R1) object. The ranges may be different, but they must have the same element type. The result...
fnauto choose(R1, R2)(bool condition, return scope R1 r1, return scope R2 r2) if (isInputRange!(Unqual!R1) && isInputRange!(Unqual!R2) && !is(CommonType!(ElementType!(Unqual!R1), ElementType!(Unqual!R2)) == void))Choose one of two ranges at runtime depending on a Boolean condition.
fnauto chooseAmong(Ranges...)(size_t index, return scope Ranges rs) if (Ranges.length >= 2 && allSatisfy!(isInputRange, staticMap!(Unqual, Ranges)) && !is(CommonType!(staticMap!(ElementType, Ranges)) == void))Choose one of multiple ranges at runtime.
fnauto roundRobin(Rs...)(Rs rs) if (Rs.length > 1 && allSatisfy!(isInputRange, staticMap!(Unqual, Rs)))roundRobin(r1) yields `r1.front`, then `r2.front`, then `r3.front`, after which it pops off one element from each and continues again from `r1`. For example, if two ranges are involved, it alternat...
fnauto radial(Range, I)(Range r, I startingIndex) if (isRandomAccessRange!(Unqual!Range) && hasLength!(Unqual!Range) && hasSlicing!(Unqual!Range) && isIntegral!I)Iterates a random-access range starting from a given point and progressively extending left and right from that point. If no initial point is given, iteration starts from the middle of the range. I...
fnauto radial(R)(R r) if (isRandomAccessRange!(Unqual!R) && hasLength!(Unqual!R) && hasSlicing!(Unqual!R))Ditto
fnTake!R take(R)(R input, size_t n) if (isInputRange!(Unqual!R))Lazily takes only up to `n` elements of a range. This is particularly useful when using with infinite ranges.
fnauto takeExactly(R)(R range, size_t n) if (isInputRange!R)Similar to take, but assumes that `range` has at least n elements. Consequently, the result of takeExactly(range) always defines the `length` property (and initializes it to `n`) even when `range` ...
fnauto takeOne(R)(R source) if (isInputRange!R)Returns a range with at most one element; for example, takeOne([42) returns a range consisting of the integer 42. Calling `popFront()` off that range renders it empty.
fnauto takeNone(R)() if (isInputRange!R)Returns an empty range which is statically known to be empty and is guaranteed to have `length` and be random access regardless of `R`'s capabilities.
fnauto takeNone(R)(R range) if (isInputRange!R)Creates an empty range from the given range in 1. If it can, it will return the same range type. If not, it will return takeExactly(range).
fnauto tail(Range)(Range range, size_t n) if (isInputRange!Range && !isInfinite!Range && (hasLength!Range || isForwardRange!Range))Return a range advanced to within `n` elements of the end of `range`.
fnR drop(R)(R range, size_t n) if (isInputRange!R)`drop` is a convenience function which calls popFrontN`(range, n)` and returns `range`. Unlike `popFrontN`, the range argument is passed by copy, not by `ref`.
fnR dropBack(R)(R range, size_t n) if (isBidirectionalRange!R)ditto
fnR dropExactly(R)(R range, size_t n) if (isInputRange!R)Similar to drop and `dropBack` but they call range.popFrontExactly(n) and `range.popBackExactly(n)` instead.
fnR dropBackExactly(R)(R range, size_t n) if (isBidirectionalRange!R)ditto
fnR dropOne(R)(R range) if (isInputRange!R)`dropOne` is a convenience function which calls `range.popFront()` and returns `range`. Unlike `popFront`, the range argument is passed by copy, not by `ref`.
fnR dropBackOne(R)(R range) if (isBidirectionalRange!R)ditto
fnRepeat!T repeat(T)(T value)Ditto
fnTake!(Repeat!T) repeat(T)(T value, size_t n)ditto
fnauto generate(Fun)(Fun fun) if (isCallable!fun)Given callable (isCallable) `fun`, create as a range whose front is defined by successive calls to `fun()`. This is especially useful to call function with global side effects (random functions), o...
fnauto generate(alias fun)() if (isCallable!fun)ditto
fnauto cycle(R)(R input) if (isInputRange!R)Ditto
fnCycle!R cycle(R)(R input, size_t index = 0) if (isRandomAccessRange!R && !isInfinite!R)Ditto
fnCycle!R cycle(R)(ref R input, size_t index = 0) if (isStaticArray!R) @systemDitto
fnauto zip(Ranges...)(Ranges ranges) if (Ranges.length && allSatisfy!(isInputRange, Ranges))Ditto
fnauto zip(Ranges...)(StoppingPolicy sp, Ranges ranges) if (Ranges.length && allSatisfy!(isInputRange, Ranges))Ditto
fnLockstep!(Ranges) lockstep(Ranges...)(Ranges ranges) if (allSatisfy!(isInputRange, Ranges))Ditto
fnLockstep!(Ranges) lockstep(Ranges...)(Ranges ranges, StoppingPolicy s) if (allSatisfy!(isInputRange, Ranges))Ditto
private fnstring lockstepReverseFailMixin(Ranges...)(bool withIndex)
fnRecurrence!(fun, CommonType!(State), State.length) recurrence(alias fun, State...)(State initial)Ditto
fnauto sequence(alias fun, State...)(State args)Ditto
fnauto iota(B, E, S)(B begin, E end, S step) if ((isIntegral!(CommonType!(B, E)) || isPointer!(CommonType!(B, E))) && isIntegral!S)Creates a range of values that span the given starting and stopping values.
fnauto iota(B, E)(B begin, E end) if (isFloatingPoint!(CommonType!(B, E)))Ditto
fnauto iota(B, E)(B begin, E end) if (isIntegral!(CommonType!(B, E)) || isPointer!(CommonType!(B, E)))Ditto
fnauto iota(E)(E end) if (is(typeof(iota(E(0), end))))Ditto
fnauto iota(B, E, S)(B begin, E end, S step) if (isFloatingPoint!(CommonType!(B, E, S)))Ditto
fnauto iota(B, E)(B begin, E end) if (!isIntegral!(CommonType!(B, E)) && !isFloatingPoint!(CommonType!(B, E)) && !isPointer!(CommonType!(B, E)) && is(typeof((ref B b) { ++ b; })) && (is(typeof(B.init < E.init)) || is(typeof(B.init == E.init))) )ditto
fnFrontTransversal!(RangeOfRanges, opt) frontTransversal( TransverseOptions opt = TransverseOptions.assumeJagged, RangeOfRanges)(RangeOfRanges rr)Ditto
fnTransversal!(RangeOfRanges, opt) transversal(TransverseOptions opt = TransverseOptions.assumeJagged, RangeOfRanges)(RangeOfRanges rr, size_t n)Ditto
fnTransposed!(RangeOfRanges, opt) transposed(TransverseOptions opt = TransverseOptions.assumeJagged, RangeOfRanges)(RangeOfRanges rr) if (isForwardRange!RangeOfRanges && isInputRange!(ElementType!RangeOfRanges) && hasAssignableElements!RangeOfRanges)Given a range of ranges, returns a range of ranges where the i'th subrange contains the i'th elements of the original subranges.
fnIndexed!(Source, Indices) indexed(Source, Indices)(Source source, Indices indices)Ditto
fnChunks!Source chunks(Source)(Source source, size_t chunkSize) if (isInputRange!Source)Ditto
fnEvenChunks!Source evenChunks(Source)(Source source, size_t chunkCount) if (isForwardRange!Source && hasLength!Source)Ditto
fnauto slide(Flag!"withPartial" f = Yes.withPartial, Source)(Source source, size_t windowSize, size_t stepSize = 1) if (isForwardRange!Source)A fixed-sized sliding window iteration of size `windowSize` over a `source` range by a custom `stepSize`.
fnauto only(Values...)(return scope Values values) if (!is(CommonType!Values == void))Assemble `values` into a range that carries all its elements in-situ.
fnauto only()()ditto
fnauto enumerate(Enumerator = size_t, Range)(Range range, Enumerator start = 0) if (isIntegral!Enumerator && isInputRange!Range)Iterate over `range` with an attached index variable.
fnauto assumeSorted(alias pred = "a < b", R)(R r) if (isInputRange!(Unqual!R))Assumes `r` is sorted by predicate `pred` and returns the corresponding SortedRange!(pred) having `r` as support. To check for sorted-ness at cost n, use isSorted.
fnauto refRange(R)(R * range) if (isInputRange!R)ditto
fnauto bitwise(R)(auto ref R range) if (isInputRange!R && isIntegral!(ElementType!R))Bitwise adapter over an integral type range. Consumes the range elements bit by bit, from the least significant bit to the most significant bit.
fnauto ref nullSink()ditto
fnauto tee(Flag!"pipeOnPop" pipeOnPop = Yes.pipeOnPop, R1, R2)(R1 inputRange, R2 outputRange) if (isInputRange!R1 && isOutputRange!(R2, ElementType!R1))Implements a "tee" style pipe, wrapping an input range so that elements of the range can be passed to a provided function or OutputRange as they are iterated over. This is useful for printing out i...
fnauto tee(alias fun, Flag!"pipeOnPop" pipeOnPop = Yes.pipeOnPop, R1)(R1 inputRange) if (is(typeof(fun) == void) || isSomeFunction!fun)Ditto
fnauto padLeft(R, E)(R r, E e, size_t n) if ( ((isInputRange!R && hasLength!R) || isForwardRange!R) && !is(CommonType!(ElementType!R, E) == void) )Extends the length of the input range `r` by padding out the start of the range with the element `e`. The element `e` must be of a common type with the element type of the range `r` as defined by C...
fnauto padRight(R, E)(R r, E e, size_t n) if ( isInputRange!R && !isInfinite!R && !is(CommonType!(ElementType!R, E) == void))Extend the length of the input range `r` by padding out the end of the range with the element `e`. The element `e` must be of a common type with the element type of the range `r` as defined by Comm...

Templates 7

tmplTake(R) if (isInputRange!(Unqual!R) && ((!isInfinite!(Unqual!R) && hasSlicing!(Unqual!R)) || is(R T == Take!T)))

ditto

tmplCycle(R) if (isInfinite!R)

ditto

tmplZipShortest(Ranges...) if (Ranges.length && __traits(compiles, { static assert(allSatisfy!(isInputRange, Ranges)); }))
tmplLockstep(Range)
tmplisTwoWayCompatible(alias fn, T1, T2)

Returns true if fn accepts variables of type T1 and T2 in any order. The following code should compile:

(ref T1 a, ref T2 b)
{
 fn(a, b);
 fn(b, a);
}

tmplSortedRange(Range, alias pred = "a < b", SortedRangeOptions opt = SortedRangeOptions.assumeSorted) if (isInstanceOf!(SortedRange, Range))

ditto

tmplisSomeFiniteCharInputRange(R)

This simplifies a commonly used idiom in phobos for accepting any kind of string parameter. The type R can for example be a simple string, chained string using

chain, chainPath or any other input range of

characters.

Only finite length character ranges are allowed with this constraint.

This template is equivalent to:

isInputRange!R && !isInfinite!R && isSomeChar!(ElementEncodingType!R)

See Also