python实现插入排序
插入排序:
分析:
我们假设第一个元素作为有序的一个序列,然后我们拿后面的元素与其有序序列进行对比,如果后者比前者小,那么我们就把元素插入到有序序列当中,
以[54,26,93,17,77,31,44,55,20]为例子。
【54】作为有序序列,26比54小,那么插入到序列当中并且称为另一个有序序列【26,54】,然后比较93与有序序列当中的54比较,【26,54,93】 17与93比较 ,17与93互换【26,54,17,93】再让17与54比较【26,17,54,93】再让17与26比较【17,26,54,93】以此类推。
因此我们可以得到每次i 要与i-1进行比较,如果i下标元素小就互换,然后再与前面的元素再比 就需要将i=i-1操作。
代码实现
def insert_sort(alist):
"""插入排序"""
n=len(alist)
#从右边的无序序列中取出多少个元素执行这样的过程
for j in range(1,n):
i=j#代表内层循环起始值
#执行从右边的无序序列取出第一个元素,即i位置的元素,然后将其插入到前面正确的位置中去
while i>0:
if alist[i]<alist[i-1]:
alist[i],alist[i-1]=alist[i-1], alist[i]
i-=1
if __name__=="__main__":
a=[54,26,93,17,77,31,44,55,20]
print("排序之前的数为:")
print(a)
print("排序之后的数为:")
insert_sort(a)
print(a)
优化代码:
def insert_sort(alist):
"""插入排序"""
n=len(alist)
#从右边的无序序列中取出多少个元素执行这样的过程
for j in range(1,n):
i=j #代表内层循环起始值
#执行从右边的无序序列取出第一个元素,即i位置的元素,然后将其插入到前面正确的位置中去
while i>0:
if alist[i]<alist[i-1]:
alist[i],alist[i-1]=alist[i-1], alist[i]
i-=1
else:
break
#i=j j-1 j-2 1
if __name__=="__main__":
a=[54,26,93,17,77,31,44,55,20]
print("排序之前的数为:")
print(a)
print("排序之后的数为:")
insert_sort(a)
print(a)
关于代码中一些理解:
while i>0:
if alist[i]<alist[i-1]:
alist[i],alist[i-1]=alist[i-1], alist[i]
i-=1
else:
break
(1)我们还是以[54,26,93,17,77,31,44,55,20]为例子,假设我们已经比较过前三个数,排序以后结果为[26,54,93,17,77,31,44,55,20] ,17的下标为i=3,我们需要将17与93进行比较,所以就是与下标为i-1的元素怒进行比较,如果后者比前者小就互换[26,54,17,93,77,31,44,55,20],此时17的下标为2,也就是i-1,这时我们还是需要比较17与前面元素的大小,[26,17,54,93,77,31,44,55,20],直到i1时结束循环,结果为[17,26,54,93,77,31,44,55,20]。
(2) 我们刚刚举例17,下标为3,也就是前提前0-2的下标元素已经时排序好的序列,我们需要进行从n次才可以全部排序完成。
(3) else:
break
这句话加入的目的时为了优化算法,针对与本来就已经时排序好的序列我们可以降低时间复杂度。[26,54,93, 17,77,31,44,55,20]
假设我们已经排序好的序列为【26,54】,现在我们需要比较93,此时93比54大,所以无序互换操作,然后进行i-1操作,实际上也就是再次比较54与26之间的大小关系,而实际上这时【26,54】已经属于排序好的有序序列。因此再次比较就属于多余的操作了。所以使用了else:break
时间复杂度:
最坏复杂度O(N*N)
优化后的复杂度O(N)