数据结构——排序(冒泡排序 直接插入排序 直接选择排序 快速排序)

这里主要讲各个排序的思想 原理 和其时间 空间复杂度

        代码什么的网上都有 CV一下就行了

        主要讲冒泡排序 直接插入排序 直接选择排序 快速排序

        其他排序不方便直接用文字讲解(我不会画图) 推荐数形结合


推荐网站:图码

数据结构可视化交互动画版 | 图码图码是一个数据结构和算法可视化交互动画版网站,皆在创建一个可以直观地学习编程、数据结构和算法的平台。囊括国内计算机考研、期末考试、408数据结构和面试的常见算法题。打造一个学习的新平台新社区。icon-default.png?t=O83Ahttps://www.totuma.cn/

冒泡排序

冒泡排序是一种简单的排序算法,基于 交换相邻元素 的思想,它通过重复地遍历待排序的元素,逐步将较大的元素“冒泡”到序列的末端。它的核心思想可以用“相邻元素两两比较并交换”的方式来理解。

时间复杂度:O(n^2)

最坏情况:当序列是反向排列时,每次遍历都需要进行元素交换。此时,冒泡排序的时间复杂度为 O(n^2)。

最好情况:当序列已经是有序的时,冒泡排序只需要进行一趟遍历,并且没有发生任何交换。此时,时间复杂度是 O(n)(可以通过设置一个标志来优化,若一趟遍历没有交换元素,则提前结束排序)。

平均情况:通常为 O(n^2),因为每对元素都要进行比较。

空间复杂度:O(1)

空间复杂度:冒泡排序是一种 原地排序算法,它只需要常数空间用于存储临时变量,因此空间复杂度是 O(1)。

稳定性:稳定

稳定

直接插入排序

直接插入排序是一种简单的排序算法,其基本思想与我们日常插入牌类游戏中的操作类似:在给扑克牌进行整理的时候 都会将其中一张牌先整理 然后在选择下一张牌有序地插入前一个数组中

假设有一组数据:

[23,54,22,56,1,45,67,6]

step1

首先将第一个数进行排序:

[23]        [54,22,56,1,45,67,6]

现在23已经排好序了(一个元素肯定是有序的) 

step2

接下来选择无序列中的第一个元素54

将其插入到有序列中

[23,54]        [22,56,1,45,67,6]

stepN 

重复上述操作

[22,23,54]        [56,1,45,67,6]

 [22,23,54,56]        [1,45,67,6]

 [1,22,23,54,56]        [45,67,6] 

 [1,22,23,45,54,56]        [67,6]  

 [1,22,23,45,54,56,67]        [6]   

 [1,6,22,23,45,54,56,67]        [ ]    

这样就完成了排序

时间复杂度:O(n^2)

时间复杂度:O(n^2)

最坏情况(逆序排列):每次插入都需要移动所有已经排好序的元素,时间复杂度为 O(n^2)。

最好情况(已排序):每次插入都不需要移动元素,时间复杂度为 O(n)。

平均情况:时间复杂度通常为 O(n^2)。

空间复杂度:O(1)

 空间复杂度:直接插入排序是一种 原地排序算法,它只需要常数空间来存储临时变量,因此空间复杂度是 O(1)。

稳定性:稳定

稳定

直接选择排序

直接选择排序是一种简单的排序算法,其核心思想是每次从待排序的元素中选出最小(或最大)元素,将其与当前待排序区间的第一个元素交换,逐步缩小待排序区间,直到所有元素都排好序。

直接选择排序的基本思想:

1. 从未排序部分中选择最小元素:每一轮排序,选择当前未排序部分中最小的元素。

2. 与当前元素交换位置:将选出的最小元素与当前待排序区间的第一个元素交换位置,确保该元素已经排好序。

3. 逐步缩小排序区间:每一轮排序都会使得一个元素排好序,直到整个序列排好序。

假设有一组数据:

[23,54,22,56,1,45,67,6]

step1

在列中找到最小的元素 与第一个元素进行交换

[23,54,22,56,1,45,67,6]

将23和1进行交换

[1,54,22,56,23,45,67,6]

现在1是有序的了

 step2

接下来选择第二小的元素与54交换

[1,54,22,56,23,45,67,6]

[1,6,22,56,23,45,67,54]

现在1,6是有序的了

stepN 

重复以上步骤

[1,6,22,56,23,45,67,54]

[1,6,22,56,23,45,67,54] //22本身是无序列中最小的了 无需交换

 [1,6,22,56,23,45,67,54]

[1,6,22,23,56,45,67,54]

[1,6,22,23,56,45,67,54] 

[1,6,22,23,45,56,67,54]

[1,6,22,23,45,56,67,54]

[1,6,22,23,45,54,67,56]

[1,6,22,23,45,54,67,56]

[1,6,22,23,45,54,56,67]

至此排序完成

时间复杂度:O(n^2)

最坏情况:每次选择最小元素都需要遍历剩下的所有元素,时间复杂度为 O(n^2)。

最好情况:即使元素已经有序,选择排序也会进行完整的比较,因此时间复杂度仍然是 O(n^2)。

平均情况:时间复杂度通常为 O(n^2)。

空间复杂度:O(1)

空间复杂度:直接选择排序是一种 原地排序算法,只需要常数空间来存储临时变量,因此空间复杂度是 O(1)。

稳定性:不稳定

不稳定

交换会打乱原来相同元素的前后顺序

快速排序

快速排序是一种高效的排序算法,其基本思想是 分治法。通过选择一个”基准(枢轴量)”元素,将待排序的数组分为两个子数组:一个子数组中所有元素都比基准元素小,另一个子数组中所有元素都比基准元素大。然后递归地对这两个子数组进行排序。

快速排序的基本思想:

                把比枢轴量小的元素丢到枢轴量前面

                把比枢轴量大的元素丢到枢轴量后面

1. 选择基准(枢轴量)元素:从待排序的数组中选择一个元素作为“基准”元素(通常是第一个元素、最后一个元素、或者中间元素)。

2. 分割数组:通过一趟排序将数组重新排列,确保基准元素左侧的所有元素都比基准元素小,右侧的所有元素都比基准元素大。

3. 递归排序子数组:对基准元素左边和右边的子数组分别递归进行快速排序,直到每个子数组的长度为 1 或 0,排序完成。

假设有一组数据:

[23,54,22,56,1,45,67,6]

step1

以23为枢轴量

将23放到哨兵位置进行保存        //相当于temp

将low指针移动到23这个元素

将high指针移动到6这个元素

发现low>high

将high赋值给low

23        [6,54,22,56,1,45,67,6]

移动low指针:low+1

现在low指向54

发现low>high

将high赋值给low

23        [6,54,22,56,1,45,67,54]

移动high指针:high-1

现在high指向67

发现high>枢轴量

pass

移动high指针:high-1

现在high指向45

发现high>枢轴量

pass

移动high指针:high-1

现在high指针指向1

发现high<枢轴量

将high赋值给low

23        [6,1,22,56,1,45,67,54]

移动low指针:low+1

现在low指向22

发现low<枢轴量

pass

移动low指针:low+1

现在low指向56

发现low>枢轴量

将low赋值给high

23        [6,1,22,56,56,45,67,54]

移动high指针:high-1

现在high指针指向56

发现low=high

将枢轴量放入low中

23        [6,1,22,23,56,45,67,54]

至此 第一趟排序结束

接下来递归地进行上述步骤即可 

 快速排序伪代码

quickSort(arr):
    if len(arr) <= 1:
        return arr
    pivot = arr[0]  # 或选择其他方法确定枢轴量
    left = [x for x in arr[1:] if x < pivot]
    right = [x for x in arr[1:] if x >= pivot]
    return quickSort(left) + [pivot] + quickSort(right)

时间复杂度:O(n log n)

最坏情况(基准选择不当,导致极端分割):当数组已经是有序的,或者选择的基准元素总是最大或最小元素时,时间复杂度为 O(n^2)。

最好情况(基准元素将数组平分为两部分):每次都将数组分成两个相等的子数组,时间复杂度为 O(n log n)。

平均情况:如果基准元素选择得较好,快速排序的时间复杂度通常为 O(n \log n)。

空间复杂度:O(logn)

空间复杂度:快速排序是一种 原地排序算法,即不需要额外的存储空间,除了递归调用栈所占的空间。空间复杂度是 O(log n),这是因为递归调用的栈深度最多为 \log n(当每次都能将数组平分时)。

稳定性:不稳定

不稳定

操作时需要与枢轴量比较大小 根据大小丢到前面或者后面 肯定不稳定

你可能感兴趣的:(数据结构,算法,排序算法)