冒泡排序和插入排序之间的区别
相信大部分人第一个学的排序就是冒泡排序,但真正应用时,可能会误写成插入排序。
因为这两种排序算法实在太像了,简直就是亲兄弟。
算法名称 最差时间复杂度 平均时间复杂度 最优时间复杂度 空间复杂度 稳定性
冒泡排序 O(N^2) O(N^2) O(N) O(1) 稳定
插入排序 O(N^2) O(N^2) O(N) O(1) 稳定
两者在数据上简直一毛一样,只考虑复杂度的话完全可以互相替代。
但深究的话,还是能找出许多不同:
打个比方:这是我们今天的主角小明,他机智勇敢热爱学习乐于助人
有一天他上体育课,排的是3号位置,老师说:同学们请用冒泡排序的方法排好队。小明觉得自己比2号的小红高,所以互换位置,成为了2号。然后他觉得比1号小刚高,所以又互换位置排到了1号。老师说:小明,滚到最后去。最终他成了100号,这就是插入排序。
插入排序:
将无序的元素插入到有序的元素序列中,插入后仍然有序
for i in 2 to n for j in i downto 2 if array[j - 1] > array[j] swap(array[j - 1], array[j]) else break /* 从小到大排列[2,1,4,3] 第一趟排序:[1,2,4,3] 交换次数:1 比较次数:1 第二趟排序:[1,2,4,3] 交换次数:0 比较次数:1 第三趟排序:[1,2,3,4] 交换次数:1 比较次数:2 从小到大排列[4,3,2,1] 第一趟排序:[3,4,2,1] 交换次数:1 比较次数:1 第二趟排序:[2,3,4,1] 交换次数:2 比较次数:2 第三趟排序:[1,2,3,4] 交换次数:3 比较次数:3 */
冒泡排序:
比较相邻元素,直到序列变为有序为止
for i in 1 to n for j in 1 to n - i if array[j] > array[j + 1] swap(array[j], array[j + 1]) /* 举例:从小到大排列[2,1,4,3] 第一趟排序:[1,2,4,3] 交换次数:1 比较次数:3 第二趟排序:[1,2,4,3] 交换次数:0 比较次数:2 第三趟排序:[1,2,3,4] 交换次数:1 比较次数:1 从小到大排列[4,3,2,1] 第一趟排序:[3,2,1,4] 交换次数:3 比较次数:3 第二趟排序:[2,1,3,4] 交换次数:2 比较次数:2 第三趟排序:[1,2,3,4] 交换次数:1 比较次数:1 */
在代码上看似差别不大,实际上两种排序的交换次数,比较次数和每趟排序后的结果不一定相同
但交换和比较操作一般视为O(1),因此两者时间复杂度相等
细心的童鞋会发现:这段冒泡排序的最差时间复杂度是O(N^2)而不是O(N)
因为实际上冒泡排序是可以优化的
for i in 1 to n flag = 0 for j in 1 to n - i if array[j] > array[j + 1] swap(array[j], array[j + 1]) flag = 1 if flag == 0 end /* 最差时间复杂度降为O(N) */