排序算法之快速排序
1.快速排序定义:
快排的主要思想:分治+迭代,只需要三步:
- 在数列之中,选择一个元素作为”基准”(pivot),或者叫比较值。
- 数列中所有元素都和这个基准值进行比较,如果比基准值小就移到基准值的左边,如果比基准值大就移到基准值的右边
- 以基准值左右两边的子列作为新数列,不断重复第一步和第二步,直到所有子集只剩下一个元素为止。
2.复杂度:
最优时间复杂度:O(nlogn)
最差时间复杂度:O(n^2)
最优空间复杂度为:O(logn) ;每一次都平分数组的情况
最差空间复杂度为:O( n ) ;退化为冒泡排序的情况
3.稳定性:
不稳定(比如基准值的前后都存在与基准值相同的元素,那么相同值就会被放在一边,这样就打乱了之前的相对顺序)
例如:【5(1),,8,5(2),2,9】通过快速排序变为【2,5(1),5(2),8,9】or【2,5(2),5(1),8,9】
4.与归并排序的区别:
归并排序与快排两种排序思想都是分而治之,但是它们分解和合并的策略不一样:归并是从中间直接将数列分成两个,而快排是比较后将小的放左边大的放右边,所以在合并的时候归并排序还是需要将两个数列重新再次排序,而快排则是直接合并不再需要排序,所以快排比归并排序更高效一些。
5.面试
- 面试官:你了解快排吗?
- 你:略知一二
- 面试官:那你讲讲快排的算法思想吧
- 你:快排基本思想是:从数据集中选取一个基准,然后让数据集的每个元素和基准值比较,小于基准值的元素放入左边分区大于基准值的元素放入右边分区,最后以左右两边分区为新的数据集进行递归分区,直到只剩一个元素。
- 面试官:快排有什么优点,有什么缺点?
- 你:分治思想的排序在处理大数据集量时效果比较好,小数据集性能差些。
- 面试官:那该如何优化?
- 你:对大规模数据集进行快排,当分区的规模达到一定小时改用插入排序,插入排序在小数据规模时排序性能较好。
- 面试官:那你能手写一个快排吗?
- 你:quick_sort = lambda array: array if len(array) <=> array[0]])
6.Python代码:
1 #coding:utf-8 2 3 def parttion(v, left, right): 4 ''' 5 :param v: 要排序的列表 6 :param left: 列表起始端 7 :param right: 列表末端 8 :return: 9 ''' 10 key = v[left] #基准 11 low = left 12 high = right 13 while low < high: 14 while (low < high) and (v[high] >= key): 15 high -= 1 16 v[low], v[high] = v[high],v[low] 17 while (low < high) and (v[low] <= key): 18 low += 1 19 v[high],v[low] = v[low],v[high] 20 v[low] = key 21 return low 22 def quicksort(v, left, right): 23 if left < right: 24 p = parttion(v, left, right) 25 quicksort(v, left, p-1) 26 quicksort(v, p+1, right) 27 return v 28 29 s = [6, 8, 1, 4, 3, 9, 5, 4, 11, 2, 2, 15, 6] 30 print("before sort:",s) 31 s1 = quicksort(s, left = 0, right = len(s) - 1) 32 print("after sort:",s1)
输出结果: