当前位置:
文档之家› 第2章 分治策略3快速排序PPT教学课件
第2章 分治策略3快速排序PPT教学课件
Type x = a[ p ]; while( true ) {
while( a[ ++i ]<x ); while( a[ - - j ]>x ); if( i >= j ) break; Swap( a[ i ], a[ j ] ); } a[ p ] = a[ j ] ; a[ j ] = x ; return j; } 2020/12/12
the positions before the pivot are smaller than or equal to the pivot and those after the pivot are larger than the pivot Exchange the pivot with the last element in the first (i.e., ≤ sublist) – the pivot is now in its final position Sort the two sublists
2020/12/12
10
2快.5速快排速序排问序题问题
i
P
全部<=p >=p
·····
j
<=p
全部>=p
如果扫描指针i和j不相交,i<j, 简单交换A[i]和A[j],再分别对i加1,j减1,然后继续扫描
j
i
P
全部<=p &l=p
如果扫描指针i和j相交,i>j, 把中轴和A[j]交换,得到该数组的一个分区。
递归求解(conquer):通过递归调用快速排序算法 分别对a[p:q-1]和a[q+1:r]进行排序。
合并(Merge):由于对a[p:q-1]和a[q+1:r]的排序是 就地进行的,所以在a[p:q-1]和a[q+1:r]都已排好 的序后步需执行任何计算a[p:r]就已排好序。
2020/12/12
65 45 50 55 85 60 80 75 70 +∞ 5 6
65 45 50 55 60 85 80 75 70 +∞ 6 5
60 45 50 55 65 85 80 75 70 +∞
2020/12/12
Figure 2-1
9
2快.5速快排速序排问序题问题
划分的过程
使用一种两次扫描子数组的方法:一次是从左到右,另 一次是从右到左,每次都把子数组的元素和中轴进行 比较。
6
2快.5速快排速序排问序题问题
快速排序
template<class Type>
a的起始位 置
void QuickSort(Type a[ ], int p,int r)
{
a的终止位置
if(p<r)
{
int q=Partition(a,p,r); QuickSort(a,p,q-1);//对左半段排序
2020/12/12
8
2快.5速快排速序排问序题问题
划分举例
(1) (2) (3) (4) (5) (6) (7) (8) (9) (10) i
p
65 70 75 80 85 60 55 50 45 +∞ 2 9
65 45 75 80 85 60 55 50 70 +∞ 3 8
65 45 50 80 85 60 55 75 70 +∞ 4 7
Partition函数负责将 a进行一次分割,返 回分割元素的位置
QuickSort(a,q+1,r);//对右半段排序
}
}
2020/12/12
7
2快.5速快排速序排问序题问题
划分过程
Partition的过程中,首先要选择一个元素,根 据其值划分数组。称该元素为中轴。
选择中轴有许多不同的策略,我们使用最简单 的策略,选择第一个元素:s = a[p]。
从左到右的扫描从第二个元素开始,希望小于中轴的 元素位于子数组的第一部分,扫描会忽略小于中轴的 元素,直到遇到第一个大于等于中轴的元素才会停止。
从右到左的扫描从最后一个元素开始,因为我们希望 大于中轴的元素位于子数组的第二部分,扫描会忽略 大于中轴的元素,直到遇到第一个小于等于中轴的元 素才会停止。
2.5 快速排序问题 QuickSort
由著名计算机科学家霍尔(C.A.R.Hoare)给出。 把原序列分成两个子问题,在被分成的两个子
问题以后不再需要归并。 被分成的两个子问题必须满足一子问题中的所
有元素都小于或等于另一子问题的任何一个元 素。
2020/12/12
1
QuickSort
Select a pivot (partitioning element) Rearrange the list so that all the elements in
i=j
P
全部<=p
=p
全部>=p
2020/12/12 如果扫描指针i指向同一元素,i=j,被指向元素的值一定等于p。
11
2快.5速快排速序排问序题问题
划分程序
template <class Type> int Partition(Type a[ ],int p,int r) {
int i = p , j = r+1 ;
A[i]>p 3
2.5 快速排序问题
选取A的某个元素t=A(s),然后将其他元素重 新排列,使A(1:n)中所有在t以前出现的元素都 小于或等于t,而在t之后出现的元素都大于或 等于t。
A(1) A(2)
… A(s-1) A(s) A(s+1) …
A(n)
经过一次划分后
A(1) A(2)
…
A(j)
2020/12/12
2
2.5 快速排序问题
基本策略是:
将数组A[1:n]分解成两个子数组B[1:p]和 B[p+1:n],使得B[1:p]中的元素均不大于 B[p+1:n]中的元素,然后分别对这里两个 数组中的元素进行排序(非降的),最后 再把两个排好序的数组接起来即可。
p
2020/12/12
A[i]≤p
每个元素都小于或等于t
2020/12/12
t
划分元素
t
A(k)
…
A(n)
每个元素都大于或等于t
4
The partition algorithm
2020/12/12
5
2.5快速排序问题
算法步骤
分解(Divide):以a[p]为基准元素将a[p:r]划分成3 段a[p:q-1],a[q]和a[q+1:r],使得a[p:q-1]中任何一 个小于等于a[q],下标q在划分过程中确定。
左侧扫描指针起 始 右侧扫描指针起始
中轴元素 移动左侧扫描指