都在代码和注释里
#a summary of sort methods
#sort methods
#----insert sort
#------straight insert sort
#------binary insert sort
#------2-road insert sort
#------table insert sort
#------shell's sort
#----exchange sort
#------bubble sort
#------quick sort
#----selection sort
#------simple selection sort
#------tree selection sort
#------heap sort
#----merge sort
#------2-road merge sort (recursion or not)
#----radix sort
#1.插入排序
#1.1 简单插入排序
# 每一次选择一个记录插入到正确的位置
def straightInsertSort(array):
L=len(array)
for i in range(1,L):
ai=array[i]
j=i-1
while j>=0:
if ai<array[j]:
array[j+1]=array[j]
j-=1
else:
break
array[j+1]=ai
#1.2 折半插入排序
# 插入过程中的查找利用折半实现
def BInsertSort(array):
L=len(array)
for i in range(1,L):
ai=array[i]
low=0
high=i-1
while low<=high:
m=(low+high)//2
if ai<array[m]:
high=m-1
else:
low=m+1
j=i-1
while j>=high+1:
array[j+1]=array[j]
j-=1
array[high+1]=ai
#1.3 shell 插入排序 (缩小增量排序)
#对直接插入排序的改进:
# 1.若待排序列为正序,则插入排序复杂度可降至O(n)
# 2.由于直接插入排序的算法简单,所以n很小时效率也比较高
#shell排序从以上两点改进插入排序
# 先将整个待排序列分割称若干子序列分别进行插入排序,待整个序列基本有序
# 后再对整体进行插入排序
#shell排序的关键是选择增量,因为它的时间是所取增量序列的函数
# 有人指出,当增量序列delta[k]=2^(t-k+1)-1 (t为排序趟数,1<=k<=t<=log2(n+1))
# 时,shell排序的时间复杂度为O(n^(3/2))
def shellInsert(array,dk): #dk为本趟排序的增量
L=len(array)
for i in range(dk,L):
ai=array[i]
j=i-dk
while j>=0:
if ai<array[j]:
array[j+dk]=array[j]
j-=dk
else:
break
array[j+dk]=ai
#最后一趟的增量一定要为1 !!!
def shellInsertSort(array,delta,t): #delta为增量序列,t为排序趟数
delta=[]
for i in range(0,t):
delta.append(pow(2,t-i)-1)
print(delta)
for k in range(0,t):
shellInsert(array,delta[k])
#2 交换排序
# 交换记录达到排序的目的
#2.1 简单交换排序(冒泡排序)
def bubbleSort(array):
L=len(array)
for i in range(0,L):
j=L-1
while j>=i:
if array[j]<array[j-1]:
t=array[j]
array[j]=array[j-1]
array[j-1]=t
j-=1
#2.2 快速排序 (改进的冒泡排序) O(nlogn)
# 通过一趟排序将待排记录分割称独立的两部分,其中一部分比另一部分的关键字小
# 再分别对这两部分进行快速排序
def quickSortPartition(array,low,high):
#对low~high部分的数进行划分,返回位置Loc,Loc左边的关键字比Loc右边的小
# 取array[high] 为支点(pivot)
pivot=array[high]
Loc=low-1 #Loc指示分割点
for i in range(low,high):
if array[i]<pivot:
Loc+=1
t=array[Loc]
array[Loc]=array[i]
array[i]=t
Loc+=1
t=array[Loc]
array[Loc]=array[high]
array[high]=t
return Loc
def quickSort(array,low,high):
if low<high:
Loc=quickSortPartition(array,low,high)
quickSort(array,low,Loc-1)
quickSort(array,Loc+1,high)
#3 选择排序
# 每一趟在n-i+1个记录中选取关键字最小的记录为有序序列中的第i个记录
# 3.1 简单选择排序
def selectSort(array):
L=len(array)
for i in range(0,L):
j=i+1
Min=i
while j<L:
if array[j]<array[Min]:
Min=j
j+=1
if Min!=i:
t=array[i]
array[i]=array[Min]
array[Min]=t
#3.2 树型选择排序 ---》堆排序
# 堆是一个完全二叉树
#堆排序对记录少的文件并不推荐,其运行时间主要在建堆和维护堆性质上
def HeapAdjust(array,s,m):
#已知array[s..m]中的关键字除了array[s]之外满足堆的定义,
# 本函数调整array[s]使array[s..m]成为一个最大堆
rc=array[s]
j=2*s
while j<=m:
if j<m and array[j]<array[j+1]:
j+=1
if rc>=array[j]:
break
array[s]=array[j]
s=j
j=2*s
array[s]=rc
def heapSort(array):
L=len(array)
#建堆的过程即为对非叶子节点调用heapAdjust的过程
for i in range(L//2-1,-1,-1):
HeapAdjust(array,i,L-1)
for j in range(L-1,0,-1):
t=array[j]
array[j]=array[0]
array[0]=t
HeapAdjust(array,0,j-1)
#4. 归并排序
# 归并的含义是将两个或两个以上的有序表重新组合成一个新的有序表
# 无论是顺序存储结构还是链表存储结构,都可以在O(n+m)的时间量级上实现
# 实现归并排序需要和待排记录等量的辅助空间,时间复杂度为O(nlogn)
def Merge(array,s,m,t):
#将array[s..m]和array[m+1..t] Merge到array[s..t]
L=array[s:m+1]
R=array[m+1:t+1]
i=0
j=0
for k in range(s,t+1):
if i<len(L) and j<len(R):
if L[i]<R[j]:
array[k]=L[i]
i+=1
else:
array[k]=R[j]
j+=1
else:
if i<len(L):
array[k]=L[i]
i+=1
else:
array[k]=R[j]
j+=1
def MergeSort(array,s,t):
if s<t:
m=(s+t)//2
MergeSort(array,s,m)
MergeSort(array,m+1,t)
# print(s,m,t)
Merge(array,s,m,t)
#5.基数排序
if __name__=='__main__':
array=[49,38,65,97,76,13,27,49]
print('before sort:'+str(array))
# straightInsertSort(array)
#BInsertSort(array)
#shellInsertSort(array,[],4)
# shellInsert(array,1)
#bubbleSort(array)
# quickSort(array,0,len(array)-1)
# selectSort(array)
#heapSort(array)
MergeSort(array,0,len(array)-1)
print('after sort:'+str(array))