其余排序方法:选择排序、冒泡排序、归并排序、快速排序、插入排序、希尔排序html
从数组中选取一个元素,以它做为比较基准,比它小的都放到数组左边;比它大的则放到右边。而后左边的数组和右边的数组也进行一样的操做。这样递归下去,最后数组就会成为一个有序的数组。python
借用一下百科的图:
数组
快速排序时不稳定的,它的最好和平均时间复杂度为O(nlogn)。
最坏的状况就是每次所选的基准都是当前序列中的最大或最小元素,这样每次划分的两个子数组中都有一个是空数组,则最终须要通过n次划分,最坏的时间复杂度为O(logn^2)。
python的递归层数是有限制的,当n大到必定程度时,就会崩掉。因此咱们应该尽可能避免最坏的状况发生。性能
Python:优化
# 快速排序 # left为第一个下标,right为最后一个下标 def quickSort(arr, left, right): if left >= right: return # 将第一位元素设为比较基准 key = arr[left] i, j = left, right # 比基准小的元素都放到左边,大的都放到右边 while i < j: while i < j and arr[j] >= key: j -= 1 arr[i] = arr[j] while i < j and arr[i] <= key: i += 1 arr[j] = arr[i] arr[i] = key # 左右两边的数组进行一样的操做 quickSort(arr, left, i - 1) quickSort(arr, i + 1, right)
快速排序的优化主要针对于最坏状况的优化,如何避免每次所选的基准都是当前序列中的最大或最小元素?
咱们一般是取第一位元素做为基准值。数组若是一开始就是有序的话,就是最坏状况了。
改进方法:
有一种方法就是在排序以前shuffle一下(打乱顺序);
还有一种是不取第一位元素,而是取第一位、最后一位和中间位中的中值元素做为基准值,这样就能彻底避免最坏状况了。ui
# 取中值 def midVal(arr, left, right): mid = left + right >> 1 if arr[mid] > arr[right]: arr[mid], arr[right] = arr[right], arr[mid] if arr[left] > arr[right]: arr[left], arr[right] = arr[right], arr[left] if arr[mid] > arr[left]: arr[left], arr[mid] = arr[mid], arr[left] return arr[left] # 快速排序 # left为第一个下标,right为最后一个下标 def quickSort(arr, left, right): if left >= right: return # 取第一位、最后一位和中间位中的中值元素做为基准值 key = midVal(arr, left, right) i, j = left, right # 比基准小的元素都放到左边,大的都放到右边 while i < j: while i < j and arr[j] >= key: j -= 1 arr[i] = arr[j] while i < j and arr[i] <= key: i += 1 arr[j] = arr[i] arr[i] = key # 左右两边的数组进行一样的操做 quickSort(arr, left, i - 1) quickSort(arr, i + 1, right)