std::ranges::min_element() algorithm
- od C++20
- Simplified
- Detailed
// (1)constexpr I min_element( I first, S last, Comp comp = {}, Proj proj = {} );// (2)constexpr ranges::borrowed_iterator_t<R> min_element( R&& r, Comp comp = {}, Proj proj = {} );The type of arguments are generic and have the following constraints:
I-std::forward_iteratorS-std::sentinel_for<I>R-std::ranges::forward_rangeComp:- (1) -
std::indirect_strict_weak_order<std::projected<I, Proj>> - (2) -
std::indirect_strict_weak_order<std::projected<ranges::iterator_t<R>, Proj>>
- (1) -
Proj- (none)
The Proj and Comp template arguments have the following default types: std::identity, ranges::less for all overloads.
Additionally, each overload has the following constraints:
- (1) -
std::sortable<I, Comp, Proj> - (2) -
std::sortable<ranges::iterator_t<R>, Comp, Proj>
// (1)template< std::forward_iterator I, std::sentinel_for<I> S, class Proj = std::identity, std::indirect_strict_weak_order<std::projected<I, Proj>> Comp = ranges::less>constexpr I min_element( I first, S last, Comp comp = {}, Proj proj = {} );// (2)template< ranges::forward_range R, class Proj = std::identity, std::indirect_strict_weak_order<std::projected<ranges::iterator_t<R>, Proj>> Comp = ranges::less>constexpr ranges::borrowed_iterator_t<R> min_element( R&& r, Comp comp = {}, Proj proj = {} );-
(1) Finds the smallest element in the range [
first;last). -
(2) Same as (1), but uses
ras the source range, as if usingranges::begin(r)asfirstandranges::end(r)aslast.
The function-like entities described on this page are niebloids.
Parameters
first last | The range to find the smallest value in. |
r | The range to find the smallest value in. |
comp | Comparison to apply to the projected elements. |
proj | Projection to apply to the elements. |
Return value
Iterator to the smallest element in the range [first; last).
If several elements in the range are equivalent to the smallest element, returns the iterator to the first such element.
Returns first if the range is empty.
Complexity
Given N as std::distance(first, last):
Exactly min(N - 1, 0) comparisons.
Exceptions
(none)
Possible implementation
min_element(1) and min_element(2)
struct min_element_fn{ template<std::forward_iterator I, std::sentinel_for<I> S, class Proj = std::identity, std::indirect_strict_weak_order<std::projected<I, Proj>> Comp = ranges::less> constexpr I operator()(I first, S last, Comp comp = {}, Proj proj = {}) const { if (first == last) return last; auto smallest = first; ++first; for (; first != last; ++first) if (!std::invoke(comp, std::invoke(proj, *smallest), std::invoke(proj, *first))) smallest = first; return smallest; } template<ranges::forward_range R, class Proj = std::identity, std::indirect_strict_weak_order< std::projected<ranges::iterator_t<R>, Proj>> Comp = ranges::less> constexpr ranges::borrowed_iterator_t<R> operator()(R&& r, Comp comp = {}, Proj proj = {}) const { return (*this)(ranges::begin(r), ranges::end(r), std::ref(comp), std::ref(proj)); }};inline constexpr min_element_fn min_element;Examples
#include <algorithm>#include <cmath>#include <iostream>#include <vector>int main(){ std::vector<int> v {3, 1, -14, 1, 5, 9}; namespace ranges = std::ranges; auto result = ranges::min_element(v.begin(), v.end()); std::cout << "min element at [" << ranges::distance(v.begin(), result) << "]\n"; auto abs_compare = [](int a, int b) { return (std::abs(a) < std::abs(b)); }; result = ranges::min_element(v, abs_compare); std::cout << "|min| element at [" << ranges::distance(v.begin(), result) << "]\n";}min element at [2]|min| element at [1]Hover to see the original license.