Scroll to navigation

std::experimental::ranges::copy,std::experimental::ranges::copy_if(3) C++ Standard Libary std::experimental::ranges::copy,std::experimental::ranges::copy_if(3)

NAME

std::experimental::ranges::copy,std::experimental::ranges::copy_if - std::experimental::ranges::copy,std::experimental::ranges::copy_if

Synopsis


Defined in header <experimental/ranges/algorithm>
template< InputIterator I, Sentinel<I> S, WeaklyIncrementable O >


requires IndirectlyCopyable<I, O> (1) (ranges TS)
ranges::tagged_pair<tag::in(I), tag::out(O)>


copy(I first, S last, O result);
template< InputRange R, WeaklyIncrementable O >


requires IndirectlyCopyable<ranges::iterator_t<R>, O>
ranges::tagged_pair<tag::in(ranges::safe_iterator_t<R>), (2) (ranges TS)
tag::out(O)>


copy(R&& r, O result);
template< InputIterator I, Sentinel<I> S, WeaklyIncrementable O,


class Proj = ranges::identity,
IndirectUnaryPredicate<projected<I, Proj>> Pred > (3) (ranges TS)
requires IndirectlyCopyable<I, O>
ranges::tagged_pair<tag::in(I), tag::out(O)>


copy_if(I first, S last, O result, Pred pred, Proj proj = Proj{});
template< InputRange R, WeaklyIncrementable O,


class Proj = ranges::identity,
IndirectUnaryPredicate<projected<ranges::iterator_t<R>, Proj>> Pred
> (4) (ranges TS)
requires IndirectlyCopyable<iterator_t<R>, O>
ranges::tagged_pair<tag::in(ranges::safe_iterator_t<R>),
tag::out(O)>


copy_if(R&& r, O result, Pred pred, Proj proj = Proj{});


Copies elements in the source range ([first,last) or r) into the destination range
beginning at result, starting from the first element in the source range and
proceeding to the last one.


1) Copies all elements in the range [first, last). For each non-negative integer n <
(last - first), performs *(result + n) = *(first + n). The behavior is undefined if
result is within the range [first, last). In this case, ranges::copy_backward may be
used instead.
2) Same as (1), but uses r as the source range, as if by
ranges::copy(ranges::begin(r), ranges::end(r), result); except that result may not
be copied.
3) Only copies the elements for which the predicate pred returns true when applied
to the element's value as projected by the projection proj. The order of the
elements that are copied is preserved. The behavior is undefined if the source and
the destination ranges overlap.
4) Same as (3), but uses r as the source range, as if by
ranges::copy_if(ranges::begin(r), ranges::end(r), result, pred, proj); except that
result, pred and proj may not be copied.


Notwithstanding the declarations depicted above, the actual number and order of
template parameters for algorithm declarations is unspecified. Thus, if explicit
template arguments are used when calling an algorithm, the program is probably
non-portable.

Parameters


first, last - the range of elements to copy
r - the range of elements to copy
result - the beginning of the destination range
pred - predicate to apply to the projected elements
proj - projection to apply to the elements

Return value


A tagged_pair object containing the following two members:


* The first member, with the tag tag::in, is the past-the-end iterator of the
source range (that is, an iterator of type I that compares equal to the sentinel
last).
* The second member, with the tag tag::out, is the past-the-end iterator of the
result range.

Complexity


1) Exactly ranges::distance(first, last) assignments.
2) Exactly ranges::distance(r) assignments.
3) Exactly ranges::distance(first, last) applications of the corresponding
projection and predicate.
4) Exactly ranges::distance(r) applications of the corresponding projection and
predicate.

Possible implementations

First version


template <InputIterator I, Sentinel<I> S, WeaklyIncrementable O>
requires IndirectlyCopyable<I, O>()
ranges::tagged_pair<tag::in(I), tag::out(O)>
copy(I first, S last, O result)
{
for (; first != last; ++first, (void)++result)
*result = *first;
return {first, result};
}

Second version


template <InputRange R, WeaklyIncrementable O>
requires IndirectlyCopyable<ranges::iterator_t<R>, O>()
ranges::tagged_pair<tag::in(ranges::safe_iterator_t<R>), tag::out(O)>
copy(R&& r, O result)
{
return ranges::copy(ranges::begin(r), ranges::end(r), result);
}
Third version
template <InputIterator I, Sentinel<I> S, WeaklyIncrementable O,
class Proj = ranges::identity,
IndirectUnaryPredicate<projected<I, Proj>> Pred>
requires IndirectlyCopyable<I, O>()
ranges::tagged_pair<tag::in(I), tag::out(O)>
copy_if(I first, S last, O result, Pred pred, Proj proj = Proj{})
{
for (; first != last; ++first) {
if (ranges::invoke(pred, ranges::invoke(proj, *first))){
*result = *first;
++result;
}
}
return {first, result};
}
Fourth version
template <InputRange R, WeaklyIncrementable O,
class Proj = ranges::identity,
IndirectUnaryPredicate<projected<ranges::iterator_t<R>, Proj>> Pred>
requires IndirectlyCopyable<ranges::iterator_t<R>, O>()
ranges::tagged_pair<tag::in(ranges::safe_iterator_t<R>), tag::out(O)>
copy_if(R&& r, O result, Pred pred, Proj proj = Proj{})
{
return ranges::copy_if(ranges::begin(r), ranges::end(r), result, pred, proj);
}

Example


The following code uses copy to both copy the contents of one vector to another and
to display the resulting vector:

// Run this code


#include <experimental/ranges/algorithm>
#include <iostream>
#include <vector>
#include <experimental/ranges/iterator>
#include <numeric>


int main()
{
// see http://en.cppreference.com/w/cpp/language/namespace_alias
namespace ranges = std::experimental::ranges;


std::vector<int> from_vector(10);
std::iota(from_vector.begin(), from_vector.end(), 0);


std::vector<int> to_vector;
ranges::copy_if(from_vector.begin(), from_vector.end(),
ranges::back_inserter(to_vector),
[](const auto i) {
return i % 3;
});
// or, alternatively,
// std::vector<int> to_vector(from_vector.size());
// std::copy(from_vector, to_vector.begin());


std::cout << "to_vector contains: ";


ranges::copy(to_vector, ranges::ostream_iterator<int>(std::cout, " "));
std::cout << '\n';
}

Output:


to_vector contains: 1 2 4 5 7 8

See also


copy copies a range of elements to a new location
copy_if (function template)
(C++11)
copy_backward copies a range of elements in backwards order
(function template)
reverse_copy creates a copy of a range that is reversed
(function template)
copy_n copies a number of elements to a new location
(function template)
fill assigns a range of elements a certain value
(function template)
remove_copy copies a range of elements omitting those that satisfy specific
remove_copy_if criteria
(function template)

2022.07.31 http://cppreference.com