算法--分治法&归并排序 python

本文介绍了分治法的设计思想,包括分解、解决和合并三个步骤。归并排序是分治法的一个典型应用,通过递归地将序列分解为两半,再进行排序和合并。文章详细解析了归并排序的Python实现,特别是关键的Merge函数和循环不等式的证明,确保了算法的正确性和效率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

设计算法

我们可以选择使用的算法设计方法有很多,插入排序使用了增量方法:在排序子数组A[1…j-1]后,将单个元素A[ j ]插入子数组的适当位置,产生排序好的子数组A[1…j]。
而这次我们将考查另一种称为“分治法”的设计方法。

分治法

分治法的思想:将原问题分解为几个规模较小的但类似于原问题的子问题,递归地求解这些子问题,然后再合并这些子问题的解来解决原问题的解。
分治模式在每层递归时都有三个步骤:
分解原问题为若干子问题,这些子问题是原问题的规模较小的实例。
解决这些子问题,递归地求解各子问题。然而,若子问题的规模足够小,则直接求解。
合并这些子问题的解成原问题的解。
归并排序算法完全遵循分治模式。直观上其操作如下:
分解:分解待排序的n个元素的序列成各具n/2个元素的两个子序列。
解决:使用归并排序递归地排序两个子序列。
合并:合并两个已排序的子序列以产生已排序的答案。
当待排序的序列长度为1时,递归“开始回升”,在这种情况下不用做任何工作,因为长度为1的每个序列都已经排好序。归并排序算法的关键操作是“合并”步骤中两个已排序序列的合并。
我们用算法中常用的伪代码来表示“合并”步骤中两个已排序序列的合并:

MERGE(A, p, q, r)           #伪代码解读,定义MERGE函数,用于合并两个排序好的序列
	n1= q - p +1                 #确定两段序列的长度n1,n2
	n2= r - q
	let L[1..n1+1] and R[1..n2+1] be new arrays   #申请两段新的数组L,R,长度分别为n1+1,n2+1 
	for i = 1 to n1
		L[i]= A[p+i-1] 			#将需要合并的第一段序列A[p...p+n1-1]]赋值给L                    
	for j = 1 to n2
		R[j] = A[q + j]			#将需要合并的第二段序列A[q...q+n2]赋值给R
		L[n1 + 1] = ∞
		R[n2 +1] = ∞           #给予两端序列底部标记,标记其到达底部
		i = 1
		j = 1                  # 重置 i,j,使i,j指向L,R的第一个元素
		for k = p to r         #开始合并,比较大小,当L[i]小于等于R[j],A[k]取L[i],i之后指向L中下一个元素
			if L[i]<=R[j]        #k是指要排序的序列的下标,每次循环迭代确定A[k]的值,之后k=k+1,确定下个元素
				A[k] = L[i]
				i = i + 1
			else             	#当L[i]不小于等于R[j]时,A[k]取R[j],j之后指向R中的下一个元素
				A[k] = R[j]
				j = j + 1

Python对归并排序的实现:

#归并算法:算法设计中分治法的体现
def Merge(A, p, q, r):
    n1 
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值