快速排序的基本思想是:
1、先从数列中取出一个数作为基准数
2、分区过程,将比这个数大的数全放到它的右边,小于或等于它的数全放到它的左边
3、再对左右区间重复第二步,直到各区间只有一个数
上述思想用代码表示:
def quick_sort(data, left, right):
if left < right:
mid = partion(data, left, right)
quick_sort(data, left, mid-1)
quick_sort(data, mid+1, right)
return data
而关键就是partion函数,如何理解这个函数呢?
看动画:
有这样一组数:

用它演示一下快排思想:
我们想把这组数搞成这个样子(快排的关键):

即:用第一个数(基准数)将整个数组分割成两部分,左边这一部分比第一个数小,右边这一部分比这个数大。
实现的过程如下:

左侧箭头所指的就是我们选择的基准数,右边箭头指的是最后一个数字。
然后用最后一个数字和基准数比较,结果是8比5大,而右边这部分我们本来就要保留大的数,所以接着比较跟8相邻的数字。

下一个是9,和8的情况一样,继续下一个。

下一个是2,2比5小,所以要把2放到左边。

这样的话,空位就跑到右边,所以这次我们要从左边进行比较,即用7跟5比较

由于7比5大,所以要把7放到放到右边空位。

这时候又该从右边比较了,1比5小,所以放到左边。

然后是4,不变

接着是6,放到右边

然后是3,比5小

然后,两个箭头碰上了

这时把5放在这个位置,就完成了整个过程。

理解了这个过程,就可以写partion函数了
def partion(data, left, right):
tmp = data[left]
while left < right:
while left < right and data[right] >= tmp:
right -= 1
data[left] = data[right]
while left < right and data[left] <= tmp:
left += 1
data[right] = data[left]
data[left] = tmp
return left
完整代码:
import random
import time
def mytime(func):
def inner(*args, **kwargs):
t1 = time.time()
func(*args, **kwargs)
t2 = time.time()
print('time costed is {}.'.format(t2 - t1))
return inner
@mytime
def quick_sort(li):
def partion(li, left, right):
tmp = li[left]
while left != right:
while left != right and li[right] >= tmp:
right -= 1
else:
li[left] = li[right]
while left != right and li[left] <= tmp:
left += 1
else:
li[right] = li[left]
li[left] = tmp
return left
def core(li, left, right):
if left < right:
mid = partion(li, left, right)
core(li, left, mid-1)
core(li, mid+1, right)
print(li)
core(li, 0, len(li)-1)
print(li)
l = list(range(1000))
random.shuffle(l)
quick_sort(l)
