Go语言新宠:pdqsort排序算法的完美打造

 更新时间:2023年10月03日 11:11:49   作者:51鳄鱼儿  
pdqsort是一种新的排序算法,特别适用于Go语言,它是由Go语言团队开发的,旨在提供高效且稳定的排序算法,pdqsort采用了一种分治的策略,将数组分成小块进行排序,然后再合并这些块,需要的朋友可以参考下

pattern-defeating-quicksort简介

pdqsort是一种不稳定的混合排序算法,采用了快速排序和插入排序的结合,以避免快速排序在小数组上的性能下降。

pdqsort还使用了一些模式避免技术,以减少分支预测错误和缓存行不命中的次数。这些优化使得pdqsort在各种情况下都表现良好,尤其是对于大型、随机分布的数据集。

pdqsort已经被广泛应用于各种编程语言和库中,如Go1.19 Rust、C++等。

复杂度
最好的情况:O(n)
平均情况:O(n*logn)
最坏的情况:O(n*logn)

pdqsort的不同版本

第一个版本

应对短序列时,算法会使用插入排序,中序列或长序列则使用快速排序;
如果快速排序效果表现不佳时,则切换成堆排序


何时会认为快速排序的效果表现不佳?

当计算累计mm 轮(这里的 m=f(n)m=f(n) , f(n)f(n) 是一个关于序列长度的函数)选取的 pivot 在本轮结束后的位置离数组两端距离小于 n/8n/8 时,即判定快速排序效果表现不好。

总结:结合插入排序、快速排序和堆排序三种排序优势。

第二个版本

在第一个版本中,由于快速排序的速度制约着pdqsort的整体排序效率。

第二个版本主要优化快速排序,具体是优化快速排序中的选取基数pivot的代码。

关于pivot的选择
使用首个元素作为 pivot:业务简单,但往往表现不佳,特别是在数组有序的情况。
遍历数组,寻找数组中位数:遍历迭代的代价高,综合表现得性能不好,尽管能带来很不错的效果。
平衡寻找 pivot 所需要的开销及 pivot 带来的性能优化:寻找近似中位数。
前两个属于比较极端的选法,而算法需要权衡pivot选取的有效性,也要考虑选取pivot的代价,第三种就是这样做的。

近似中位数选取方法如下:

n⩽8n⩽8 时在纯快排里pivot会直接选固定元素,但在pdqsort里这种规模的序列会直接用插入排序。
n⩽50n⩽50 时,采样三个元素,选择三个元素中的中位数。
n>50n>50 时,采样九个元素,选择九个元素中的中位数。

第三个版本

主要解决如何优化重复元素很多的情况

重复元素较多的情况(partitionEqual)

当检测到此时的 pivot 和上次相同时(发生在 leftSubArray),即partition进行了无效分割,此时认为pivot的值为重复元素,使用 partitionEqual 将重复元素排列在一起,减少重复元素对于 pivot 选择的干扰
当 pivot 选择策略表现不佳时,随机交换元素

避免一些极端情况使得 QuickSort 总是表现不佳,以及一些黑客攻击情况

pdqsort是一种新的排序算法,专为Go语言而设计。它采用了分治的策略,将数组分成小块进行排序,然后再合并这些块。这种策略使得pdqsort在处理大规模数据时表现出色。此外,pdqsort还具有自适应的特性,可以根据输入数据的特点进行优化,从而提高排序的效率。pdqsort的设计和实现经过了精心的打造,旨在提供高效且稳定的排序算法。对于Go语言的开发者来说,pdqsort是一个非常有价值的选择。它不仅可以提高排序的效率,还可以减少开发者的工作量。因此,pdqsort是Go语言新宠,值得开发者们去尝试和使用。

到此这篇关于Go语言新宠:pdqsort排序算法的完美打造的文章就介绍到这了,更多相关打造Go语言的pdqsort排序算法内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • go HTTP2 的头部压缩算法hpack实现详解

    go HTTP2 的头部压缩算法hpack实现详解

    这篇文章主要为大家介绍了go HTTP2 的头部压缩算法hpack实现详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2022-10-10
  • 在Go语言中使用JSON的方法

    在Go语言中使用JSON的方法

    这篇文章主要介绍了在Go语言中使用JSON的相关资料,需要的朋友可以参考下
    2018-02-02
  • GO 切片删除元素的三种方法

    GO 切片删除元素的三种方法

    本文主要介绍了GO 切片删除元素,根据要删除元素的位置有三种情况,分别是从开头位置删除、从中间位置删除和从尾部删除,具有一定的参考价值,感兴趣的可以了解一下
    2024-08-08
  • Goland调节字体大小的设置(编辑区,terminal区,页面字体)

    Goland调节字体大小的设置(编辑区,terminal区,页面字体)

    这篇文章主要介绍了Goland调节字体大小的设置(编辑区,terminal区,页面字体),具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2020-12-12
  • 深入分析Go 实现 MySQL 数据库事务

    深入分析Go 实现 MySQL 数据库事务

    本文深入分析了Go语言实现MySQL数据库事务的原理和实现方式,包括事务的ACID特性、事务的隔离级别、事务的实现方式等。同时,本文还介绍了Go语言中的事务处理机制和相关的API函数,以及如何使用Go语言实现MySQL数据库事务。
    2023-06-06
  • Go Excelize API源码解析GetSheetFormatPr使用示例

    Go Excelize API源码解析GetSheetFormatPr使用示例

    这篇文章主要为大家介绍了Go Excelize API源码解析GetSheetFormatPr使用示例详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2022-08-08
  • Linux中Go环境配置和GoModule常用操作

    Linux中Go环境配置和GoModule常用操作

    这篇文章主要介绍了Linux中Go环境配置和GoModule,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2022-01-01
  • GO语言获取系统环境变量的方法

    GO语言获取系统环境变量的方法

    这篇文章主要介绍了GO语言获取系统环境变量的方法,实例分析了Getenv方法操作环境变量的技巧,具有一定参考借鉴价值,需要的朋友可以参考下
    2015-02-02
  • Go语言基础函数包的使用学习

    Go语言基础函数包的使用学习

    本文通过一个实现加减乘除运算的小程序来介绍go函数的使用,以及使用函数的注意事项,并引出了对包的了解和使用,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-05-05
  • gorm 结构体中 binding 和 msg 结构体标签示例详解

    gorm 结构体中 binding 和 msg 结构体标签示例详解

    文章介绍了Gin框架中binding和msg结构体标签的使用,包括基本用法、常用验证规则、自定义验证器、错误信息自定义、控制器使用示例、组合验证规则、跨字段验证和初始化验证器等,这些标签主要用于数据验证、自定义错误信息、参数绑定和表单验证
    2024-11-11

最新评论