std::is_sorted是c++11起标准库提供的最安全高效的有序性检测工具,时间复杂度o(n),支持升序、降序及自定义谓词,要求随机访问迭代器,语义清晰且不易出错。

用 std::is_sorted 最快最安全
标准库提供了直接可用的工具,不需要手写循环。C++11 起,std::is_sorted 就是为此设计的,它在 <algorithm></algorithm> 头文件里。
它默认按升序判断,时间复杂度 O(n),且对空数组或单元素数组返回 true(符合数学定义)。
- 升序判断:
std::is_sorted(arr, arr + n) - 降序判断:传入
std::greater<int>()</int>作为第三个参数,如std::is_sorted(arr, arr + n, std::greater<int>())</int> - 自定义比较:可传任意二元谓词,比如判断是否“非严格递增”(允许相等),就用
std::less_equal<int>()</int>
手写循环时别漏掉边界和相等情况
自己遍历判断看似简单,但容易出错。常见错误包括:越界访问、忽略相等元素是否合法、混淆升序/降序逻辑。
升序(允许相等)的正确写法是检查每一对相邻元素:a[i] ,且 <code>i 最大只能到 n-2。
- 错误示例:
for (int i = 0; i a[i+1])→ 访问a[n],越界 - 正确范围:
for (int i = 0; i - 若要求“严格升序”,用
;若允许重复(如排序后去重前),必须用 <code> - 降序同理,用
>=或>,别反着写
注意 std::is_sorted 对迭代器的要求
它要求传入的是**随机访问迭代器**(如数组指针、std::vector::begin()),不能用于 std::list 或 std::forward_list 的原生迭代器——那些不支持 it + n 运算,编译会失败。
- 对
std::list,只能手写循环 + 双指针遍历(std::next(it)) - 对
std::vector或裸数组,std::is_sorted是首选,无额外开销 - 若容器类型不确定,先确认其迭代器类别,或统一用基于范围的写法:
std::is_sorted(c.begin(), c.end())
性能差异其实可以忽略,但语义清晰更重要
手写循环和 std::is_sorted 在底层几乎一样:都是单次遍历、短路退出(发现一处不满足立刻返回 false)。编译器优化后,汇编级差异极小。
- 真正差别在于可读性:
std::is_sorted明确表达了“我在检查有序性”,而不是一段需要推理的循环 - 维护风险:手写循环容易在修改条件(比如从升序改成降序)时漏改某处符号
- 注意:如果数组很大且大概率无序,早退出优势明显;但如果总是要走到最后(比如已排序数组),两者完全等价
实际项目里,除非在极度受限的嵌入式环境(没 STL),否则直接用 std::is_sorted。最容易被忽略的是比较函数的一致性——比如用 std::less<double>()</double> 判断浮点数组时,要注意 NaN 导致的未定义行为。
C++免费学习笔记(深入):立即使用
在学习笔记中,你将探索 C++ 的入门与实战技巧!











