• 选择排序&归并排序&基数排序


    ---

    Selection Sort

    ”选择排序 “

    ”每一趟将待排序的最小元素(或最大元素)加入有序子序列 “

    image-20210701211159456

    简单选择排序

    算法实现

    image-20210701211303931

    性能分析

    image-20210701211502921

    image-20210701211542088

    Heap Sort

    ”堆排序 “

    在回顾一下6.006中对与的定义,

    image-20210701212442203

    结合之前学到的二叉树的顺序存储就不难理解了

    ”堆是一个顺序存储的完全二叉树“

    image-20210701212542234

    image-20210701212840867

    了解了大根堆和小根堆的定义后,再回来看选择排序的核心思路:

    ”每一趟将待排序的最小元素(或最大元素)加入有序子序列 “

    显然,如果我们已经拥有了一个大根堆/小根堆,上述的选择操作自然就变得十分简单,无非是取根结点的元素罢了,那么如何构造大根堆/小根堆呢?

    Build a Max_heap

    image-20210702133041886

    代码解释

    • HeadAdjust函数会将以k为根的子树调整为大根堆其使用前提是A[k]的左右子树已经是大根堆!
    • i=2*k指向结点k的左孩子,if( i<len&&A[i]<A[i+1] ) i++;会使 i 指向k的左右孩子中较大的那个
    • 一次循环内实际上只针对两个结点处理:父结点A[k]较大的那个子结点A[i],而不必考虑更下层的结点 ——(分治)
    • BuildMaxHeap的调整顺序是从后往前,这十分重要! 因为这对应到逻辑图便是从下往上调整,稍微思考一下不难发现,从下往上的处理顺序可以保证在开始处理某个结点A[k]时,它的左右子树均已经是大根堆叶子节点可以看作是特殊的大根堆 /小根堆),这也是6.006中强调的single violation,其同时也保证了上一条所述(分治)的正确性

    image-20210702135741346

    • 由于一次循环可能会破坏以A[i]为根的子树的大根堆性质,因此如果这次循环后发生了结点调整,则使k指向发生变动的那颗子树(所谓的“下沉”),开始下一次循环判断这棵子树还是不是大根堆

    基于大根堆进行排序

    既然已经知道了如何构造大根堆,那么利用它进行排序就十分简单了:

    • 将根节点A[1]与末尾结点A[len]互换,--len,表示待排序的元素个数减一
    • 调用HeadAdjust(A,1,len)将堆调整为大根堆 (思考:为什么不用BuildMaxHeap(A,len)?)

    重复上述步骤直至元素有序

    image-20210702142559166

    性能分析

    关键在于 “下坠 ”过程,即分析 HeadAdjust函数:

    image-20210702143444225

    image-20210702144143909

    link:https://www.cnblogs.com/potofsalt/p/14773949.html#heap_sort

    “堆排序不具有稳定性 ”

    image-20210702144418579

    小结

    image-20210702144518422

    堆的插入删除

    插入新结点

    ”Now I‘m rising “

    image-20210702145722593

    image-20210702150828027

    删除一个结点

    ”when i was drowning“

    image-20210702145627496

    ”考试有时会考关键字的比较次数

    image-20210702145915025

    image-20210702150001857

    image-20210702150325821

    image-20210702151302154

    Merge Sort

    ”归并排序 ”

    ”与前述的交换、选择等排序思想不一样,归并的含义是将两个或两个以上的有序表组合成一个新的有序表 “

    二路归并:将两个有序表合并为一个新的有序表

    image-20210702160934543

    image-20210702161305716

    “内部排序中一般采用二路归并 ”

    image-20210702161513491

    算法实现

    “归并 ”

    image-20210702162308854

    “归并排序 ”

    image-20210702163144916

    性能分析

    image-20210702165123913

    image-20210702164830016

    小结

    image-20210702165448226

    Radix Sort

    “基数排序 ”

    image-20210702185330099

    “要求能够手动模拟排序过程 ”

    image-20210702190216624

    image-20210702190415498

    性能分析

    image-20210702191006198

    image-20210702191505129

    收集 Q[i]上的所有元素的时间复杂度为O(1),因为只需将Q[i]的 front指针赋给表尾指针 p的 next即可 “

    image-20210702192035136

    image-20210702192346873

    Application

    image-20210702192601563

    image-20210702193039134

    image-20210702193243688

    小结

    image-20210702193723205

  • 相关阅读:
    task-clph
    遍历数组的方式
    iOS事件处理之七种手势
    quatz2d使用注意点
    iOS 细碎知识整理
    九宫格算法图示
    mac10.12的Cocopods安装使用
    静态库冲突的解决办法:duplicate symbol
    ceshi
    xmpp4-总览
  • 原文地址:https://www.cnblogs.com/potofsalt/p/14964663.html
Copyright © 2020-2023  润新知