【C++学习记录】std::sort()

一.源码分析

cpp 复制代码
_EXPORT_STD template <class _RanIt, class _Pr>
_CONSTEXPR20 void sort(const _RanIt _First, const _RanIt _Last, _Pr _Pred) { // order [_First, _Last)
    _Adl_verify_range(_First, _Last);
    const auto _UFirst = _Get_unwrapped(_First);
    const auto _ULast  = _Get_unwrapped(_Last);
    _Sort_unchecked(_UFirst, _ULast, _ULast - _UFirst, _Pass_fn(_Pred));
}
cpp 复制代码
template <class _RanIt, class _Pr>
_CONSTEXPR20 void _Sort_unchecked(_RanIt _First, _RanIt _Last, _Iter_diff_t<_RanIt> _Ideal, _Pr _Pred) {
    // order [_First, _Last)
    for (;;) {
        if (_Last - _First <= _ISORT_MAX) { // small
            _Insertion_sort_unchecked(_First, _Last, _Pred);
            return;
        }

        if (_Ideal <= 0) { // heap sort if too many divisions
            _Make_heap_unchecked(_First, _Last, _Pred);
            _Sort_heap_unchecked(_First, _Last, _Pred);
            return;
        }

        // divide and conquer by quicksort
        auto _Mid = _Partition_by_median_guess_unchecked(_First, _Last, _Pred);

        _Ideal = (_Ideal >> 1) + (_Ideal >> 2); // allow 1.5 log2(N) divisions

        if (_Mid.first - _First < _Last - _Mid.second) { // loop on second half
            _Sort_unchecked(_First, _Mid.first, _Ideal, _Pred);
            _First = _Mid.second;
        } else { // loop on first half
            _Sort_unchecked(_Mid.second, _Last, _Ideal, _Pred);
            _Last = _Mid.first;
        }
    }

函数逻辑

  1. 小范围排序 :如果待排序范围小于或等于 _ISORT_MAX (32),则直接使用插入排序进行排序。插入排序在小范围内通常比快速排序更快,因为它的常数开销更小。

  2. 堆排序 :如果 _Ideal(表示理想的分割次数)小于等于 0,表示递归深度超过了限制,此时使用堆排序来避免快速排序的最坏情况(例如当输入已经排序时,快速排序的时间复杂度为 O(n²))。

  3. 快速排序 :在快速排序部分,该算法会使用 _Partition_by_median_guess_unchecked 函数来选择枢轴元素,将待排序范围划分成两部分,然后递归地对两部分分别进行排序:调整理想分割次数 :++根据当前分割次数减少 _Ideal 的值,以控制递归深度。通过右移操作,_Ideal 会递减,从而限制递归深度。++

  4. 递归排序 :根据子数组的大小选择先递归处理哪个部分,以减少栈的深度:++如果左半部分小于右半部分,则优先处理左半部分,接着处理右半部分。否则先处理右半部分。++

二.自定义比较函数的4种方法

​​​​​​https://www.cnblogs.com/kazusarua/p/17960553

相关推荐
ragnwang2 小时前
C++ Eigen常见的高级用法 [学习笔记]
c++·笔记·学习
lqqjuly5 小时前
特殊的“Undefined Reference xxx“编译错误
c语言·c++
冰红茶兑滴水5 小时前
云备份项目--工具类编写
linux·c++
刘好念5 小时前
[OpenGL]使用 Compute Shader 实现矩阵点乘
c++·计算机图形学·opengl·glsl
酒鬼猿6 小时前
C++进阶(二)--面向对象--继承
java·开发语言·c++
姚先生976 小时前
LeetCode 209. 长度最小的子数组 (C++实现)
c++·算法·leetcode
小王爱吃月亮糖7 小时前
QT开发【常用控件1】-Layouts & Spacers
开发语言·前端·c++·qt·visual studio
aworkholic7 小时前
opencv sdk for java中提示无stiching模块接口的问题
java·c++·opencv·jni·opencv4android·stiching
程序员老冯头7 小时前
第十六章 C++ 字符串
开发语言·c++
Xenia2237 小时前
复习篇~第二章程序设计基础
c++·算法