快速排序是一种常用的排序算法,比选择排序快得多。例如,C语言标准库中的函数qsort 实现的就是快速排序。快速排序也使用了D&C。(分而治之)
(1) 找出简单的基线条件;
(2) 确定如何缩小问题的规模,使其符合基线条件。 D&C并非可用于解决问题的算法,而是一种解决问题的思路。我们再来看一个例子。 给定一个数字数组。
# -*- coding: utf-8 -*- """ @author:songhao @file: c3.py @time: 2017/12/26 """ import random def quiksort(arr): """ 实现快速排序 :param arr: :return: """ if len(arr) < 2: return arr # 基线条件:为空或只包含一个元素的数组是“有序”的 else: pivot = arr[0] # 递归条件 less = [x for x in arr[1:] if x <= pivot] # 由所有小于基准值的元素组成的子数组 large = [z for z in arr[1:] if z > pivot] #由所有大于基准值的元素组成的子数组 print('less', arr, less) print('large', arr, large) print('分割线'.center(30, '#')) return quiksort(large) + [pivot] + quiksort(less) # 递归调用 if __name__ == '__main__': new = [random.choice(range(10)) for x in range(10)] print(new) # new = [1, 3, 5] print(quiksort(new))
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
|
# -*- coding: utf-8 -*-
"""
@author:songhao
@file: c3.py
@time: 2017/12/26
"""
import
random
def
quiksort
(
arr
)
:
"""
实现快速排序
:param arr:
:return:
"""
if
len
(
arr
)
<
2
:
return
arr
# 基线条件:为空或只包含一个元素的数组是“有序”的
else
:
pivot
=
arr
[
0
]
# 递归条件
less
=
[
x
for
x
in
arr
[
1
:
]
if
x
<=
pivot
]
# 由所有小于基准值的元素组成的子数组
large
=
[
z
for
z
in
arr
[
1
:
]
if
z
>
pivot
]
#由所有大于基准值的元素组成的子数组
print
(
'less'
,
arr
,
less
)
print
(
'large'
,
arr
,
large
)
print
(
'分割线'
.
center
(
30
,
'#'
)
)
return
quiksort
(
large
)
+
[
pivot
]
+
quiksort
(
less
)
# 递归调用
if
__name__
==
'__main__'
:
new
=
[
random
.
choice
(
range
(
10
)
)
for
x
in
range
(
10
)
]
print
(
new
)
# new = [1, 3, 5]
print
(
quiksort
(
new
)
)
|
返回结果是:
快速排序 速度很快
递归调用算法:
""" # @Date: 2018-4-10 # @Project: 算法 # @Filename: quicksort.py # @Last modified by: songhao # @Copyright: 网址:www.168seo.cn 微信公众号:zeropython """ def quick_sort(alist, start, end): """快速排序 #在对快速排序优化的时候牢记一点:能够将列表均衡分开的标定点才是好的标定点。均匀分开意味着保持logn的复杂度。 #这里我并没有实现单路快排 快速排序是一种常用的排序算法,比选择排序快得多。例如,C语言标准库中的函数qsort 实现的就是快速排序。快速排序也使用了D&C。(分而治之) (1) 找出简单的基线条件; (2) 确定如何缩小问题的规模,使其符合基线条件。 D&C并非可用于解决问题的算法,而是一种解决问题的思路。我们再来看一个例子。 给定一个数字数组。 """ # 递归的退出条件 if start >= end: return # 设定起始元素为要寻找位置的基准元素 mid = alist[start] # low为序列左边的由左向右移动的游标 low = start # high为序列右边的由右向左移动的游标 high = end while low < high: # 如果low与high未重合,high指向的元素不比基准元素小,则high向左移动 while low < high and alist[high] >= mid: high -= 1 # 将high指向的元素放到low的位置上 alist[low] = alist[high] # 如果low与high未重合,low指向的元素比基准元素小,则low向右移动 while low < high and alist[low] < mid: low += 1 # 将low指向的元素放到high的位置上 alist[high] = alist[low] # 退出循环后,low与high重合,此时所指位置为基准元素的正确位置 # 将基准元素放到该位置 alist[low] = mid # 对基准元素左边的子序列进行快速排序 quick_sort(alist, start, low-1) # 对基准元素右边的子序列进行快速排序 quick_sort(alist, low+1, end) if __name__ == '__main__': alist = [54,26,93,17,77,31,44,55,20] quick_sort(alist,0,len(alist)-1) print(alist) """ """ # @Date: 2018-4-10 # @Project: 算法 # @Filename: quicksort.py # @Last modified by: songhao # @Copyright: 网址:www.168seo.cn 微信公众号:zeropython """ def quicksort(data): left = 0 right = len(data) - 1 # if left > right: return quick_sort_x(data, left, right) def quick_sort_x(data, left, right): if left < right: mid = partition(data, left, right) quick_sort_x(data, left, mid - 1) quick_sort_x(data, mid + 1, right) def partition(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 """
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
|
"""
# @Date: 2018-4-10
# @Project: 算法
# @Filename: quicksort.py
# @Last modified by: songhao
# @Copyright: 网址:www.168seo.cn 微信公众号:zeropython
"""
def
quick_sort
(
alist
,
start
,
end
)
:
"""快速排序
#在对快速排序优化的时候牢记一点:能够将列表均衡分开的标定点才是好的标定点。均匀分开意味着保持logn的复杂度。
#这里我并没有实现单路快排
快速排序是一种常用的排序算法,比选择排序快得多。例如,C语言标准库中的函数qsort 实现的就是快速排序。快速排序也使用了D&C。(分而治之)
(1) 找出简单的基线条件;
(2) 确定如何缩小问题的规模,使其符合基线条件。
D&C并非可用于解决问题的算法,而是一种解决问题的思路。我们再来看一个例子。 给定一个数字数组。
"""
# 递归的退出条件
if
start
>=
end
:
return
# 设定起始元素为要寻找位置的基准元素
mid
=
alist
[
start
]
# low为序列左边的由左向右移动的游标
low
=
start
# high为序列右边的由右向左移动的游标
high
=
end
while
low
<
high
:
# 如果low与high未重合,high指向的元素不比基准元素小,则high向左移动
while
low
<
high
and
alist
[
high
]
>=
mid
:
high
-=
1
# 将high指向的元素放到low的位置上
alist
[
low
]
=
alist
[
high
]
# 如果low与high未重合,low指向的元素比基准元素小,则low向右移动
while
low
<
high
and
alist
[
low
]
<
mid
:
low
+=
1
# 将low指向的元素放到high的位置上
alist
[
high
]
=
alist
[
low
]
# 退出循环后,low与high重合,此时所指位置为基准元素的正确位置
# 将基准元素放到该位置
alist
[
low
]
=
mid
# 对基准元素左边的子序列进行快速排序
quick_sort
(
alist
,
start
,
low
-
1
)
# 对基准元素右边的子序列进行快速排序
quick_sort
(
alist
,
low
+
1
,
end
)
if
__name__
==
'__main__'
:
alist
=
[
54
,
26
,
93
,
17
,
77
,
31
,
44
,
55
,
20
]
quick_sort
(
alist
,
0
,
len
(
alist
)
-
1
)
print
(
alist
)
"""
"""
# @Date: 2018-4-10
# @Project: 算法
# @Filename: quicksort.py
# @Last modified by: songhao
# @Copyright: 网址:www.168seo.cn 微信公众号:zeropython
"""
def quicksort(data):
left = 0
right = len(data) - 1
#
if left > right:
return
quick_sort_x(data, left, right)
def quick_sort_x(data, left, right):
if left < right:
mid = partition(data, left, right)
quick_sort_x(data, left, mid - 1)
quick_sort_x(data, mid + 1, right)
def partition(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
"""
|