std::minmax
從 cppreference.com
在標頭 <algorithm> 定義
|
||
template< class T > std::pair<const T&, const T&> minmax( const T& a, const T& b ); |
(1) | (C++11 起) (C++14 起為 constexpr ) |
template< class T, class Compare > std::pair<const T&, const T&> minmax( const T& a, const T& b, |
(2) | (C++11 起) (C++14 起為 constexpr ) |
template< class T > std::pair<T, T> minmax( std::initializer_list<T> ilist ); |
(3) | (C++11 起) (C++14 起為 constexpr ) |
template< class T, class Compare > std::pair<T, T> minmax( std::initializer_list<T> ilist, |
(4) | (C++11 起) (C++14 起為 constexpr ) |
返回給定值的最小和最大者。
1,2) 返回到 a 的 b 較小和較大者的引用。
1) 使用 operator< 來比較兩個值。
如果
T
不可小於比較 (LessThanComparable) ,那麼行為未定義。2) 使用比較函數 comp 來比較兩個值。
3,4) 返回初始化器列表 ilist 中值的最小和最大者。
3) 使用 operator< 來比較這些值。
如果
T
不可小於比較 (LessThanComparable) ,那麼行為未定義。4) 使用比較函數 comp 來比較這些值。
目錄 |
[編輯] 參數
a, b | - | 要比較的值 |
ilist | - | 擁有要比較的值的初始化器列表 |
cmp | - | 比較函數對象(即滿足比較 (Compare) 要求的對象),如果a 小於 b,則返回 true。 比較函數的簽名應等價於如下: bool cmp(const Type1 &a, const Type2 &b); 雖然簽名不必有 const&,函數也不能修改傳遞給它的對象,而且必須能夠接受(可有 const 限定的)類型 |
[編輯] 返回值
1,2) 如果 a < b 或者 a 等價於 b,那麼返回 std::pair<const T&, const T&>(a, b) 的結果。如果 b < a,那麼返回 std::pair<const T&, const T&>(b, a) 的結果。
3,4) 以 ilist 中最小元素為第一元素,最大元素為第二元素的 pair。如果有多個等價於最小者的值,那麼返回最左側的這種值。如果有多個等價於最大者的值,那麼返回最右側的這種值。
[編輯] 複雜度
1) 應用一次 operator< 進行比較。
2) 應用一次比較函數 comp。
3,4) 給定 N 為 ilist.size():
3) 最多應用
次 operator< 進行比較。
3N |
2 |
4) 最多應用
次比較函數 comp。
3N |
2 |
[編輯] 可能的實現
minmax (1) |
---|
minmax (2) |
minmax (3) |
template<class T> constexpr std::pair<T, T> minmax(std::initializer_list<T> ilist) { auto p = std::minmax_element(ilist.begin(), ilist.end()); return std::pair(*p.first, *p.second); } |
minmax (4) |
template<class T, class Compare> constexpr std::pair<T, T> minmax(std::initializer_list<T> ilist, Compare comp) { auto p = std::minmax_element(ilist.begin(), ilist.end(), comp); return std::pair(*p.first, *p.second); } |
[編輯] 註解
對於重載 (1,2),如果實參之一是臨時量,那麼返回的引用在包含對 minmax
調用的完整表達式結尾變為懸垂引用:
int n = 1; auto p = std::minmax(n, n + 1); int m = p.first; // ok int x = p.second; // 未定义行为 // 注意结构化绑定有同样的问题 auto [mm, xx] = std::minmax(n, n + 1); xx; // 未定义行为
[編輯] 示例
運行此代碼
#include <algorithm> #include <cstdlib> #include <ctime> #include <iostream> #include <vector> int main() { std::vector<int> v{3, 1, 4, 1, 5, 9, 2, 6}; std::srand(std::time(0)); std::pair<int, int> bounds = std::minmax(std::rand() % v.size(), std::rand() % v.size()); std::cout << "v[" << bounds.first << "," << bounds.second << "]:"; for (int i = bounds.first; i < bounds.second; ++i) std::cout << v[i] << ' '; std::cout << '\n'; }
可能的輸出:
v[2,7]:4 1 5 9 2
[編輯] 缺陷報告
下列更改行為的缺陷報告追溯地應用於以前出版的 C++ 標準。
缺陷報告 | 應用於 | 出版時的行為 | 正確行為 |
---|---|---|---|
LWG 2239 | C++11 | 重載 (2,4) 中 T 需要可小於比較 (LessThanComparable)
|
不需要 |
[編輯] 參閱
返回給定值中較小者 (函數模板) | |
返回給定值中較大者 (函數模板) | |
(C++11) |
返回範圍中的最小元和最大元 (函數模板) |
(C++20) |
返回兩個元素間的較小者和較大者 (算法函數對象) |