总体规划
十大排序算法:冒泡排序,选择排序,插入排序,希尔排序,归并排序,快速排序,堆排序,计数排序,桶排序,基数排序。
排序思想、代码、时间复杂度、稳定性、是否原地排序。
稳定性:原来待排的元素中有相同元素,没排序之前有先后顺序,排完后他们的先后顺序不变,就称这个算法是稳定的。
原地排序:只占用小的常数内存,利用原来存储待排数据的内存来进行操作。
冒泡排序
从第一个开始,不断与右边相邻元素比较,如果左大于右就交换,直到最后最大的在最右边,这是第一趟排序。第二趟在前n-1个中重复操作,得到n个中第二大的,放在倒数第二个位置。排好序需要n-1趟,第i趟需要比较n-i次。
# 冒泡排序
def bubbleSort(arr):
for i in range(len(arr) - 1): #从最后一个位置排到第二个位置,剩下一个不需要排
for j in range(len(arr) - 1 - i): #注意下标不要溢出
if arr[j] > arr[j + 1]:
arr[j], arr[j + 1] = arr[j + 1], arr[j]
return arr
print(bubbleSort(arr))
时间复杂度:(n-1)+(n-2)+...+2+1=n(n-1)/2 O(n^2)
稳定性:稳定,如果相同不会交换。
是否原地排序:是原地排序。
优化版本:如果某一趟一直没有交换,说明已经有序了。flag=TRUE,如果左大于右{flag=FALSE,交换}。
def bubbleSortImprove(arr):
if len(arr) < 2:
return arr
for i in range(len(arr) - 1):
flag = True
for j in range(len(arr) - 1 - i):
if arr[j] > arr[j + 1]:
flag = False #False就是进行过交换
arr[j], arr[j + 1] = arr[j + 1], arr[j]
if flag: #True没有进行过交换,说明已经有序了
break
return arr
print(bubbleSortImprove(arr))
选择排序
选择排序就是不断地从未排序的元素中选择最大(或最小)的元素放入已排好序的元素集合中,直到未排序中仅剩一个元素为止。
先从这些元素中选出一个最小的(或最大的),和第一个元素进行交换,这样第一个元素就是最小的,第一个元素位置就变成有序区间了,同理,在剩下的无序区间选择最小的元素,将最小元素与无序区间的第一个元素进行交换,交换后原来无序区间的第一个元素就变为有序区间的最后一个元素了,有序区间递增一,以此类推,全部元素就可以通过这样不断地选择以及交换排完序。
如何选出最小的一个元素:先选无序区间第一个元素,然后让这个元素与无序区间中的每一个元素进行比较,如果遇到比自己小的元素,那更新最小值下标,直到把无序区间遍历完,那最后的最小值就是这个无序区间的最小值。
# 选择排序
def selectSort(arr):
for i in range(len(arr) - 1): #最后一个元素不需要排
minIndex = i #i左边是有序区间,右边(包括i)是无序区间
for j in range(i + 1, len(arr)):
if arr[j] < arr[minIndex]:
minIndex = j
if i != minIndex:
arr[i], arr[minIndex] = arr[minIndex], arr[i]
return arr
print(selectSort(arr))
时间复杂度:(n-1)+(n-2)+...+2+1=n(n-1)/2 O(n^2)
稳定性:不稳定,相同的前一个数可能会被后面更小的数换到后面去。
是否原地排序:是原地排序。
插入排序
适用处理数据量比较少或者部分有序的数据。
直接插入排序就是把右边无序区间中的数x一个个插入到左边有序区间中去,先用一个临时变量把x存起来,然后从后往前判断,如果y>x就把y往后挪一位,如果y<=x就把x插入到y后面。
# 插入排序
def insertionSort(arr):
for i in range(1,len(arr)): #第一个元素可认为是有序的,从第二个开始
temp = arr[i]
j = i - 1
while j >= 0 and arr[j] > temp: #遍历的元素比待插入的元素大
arr[j + 1] = arr[j]
j -= 1
arr[j + 1] = temp
return arr
print(insertionSort(arr))
时间复杂度:最坏的情况是倒序,外层1到n-1,内层1+2+...+(n-1)=n(n-1)/2 O(n^2)
稳定性:稳定,后面的数相等时也是放在后面的。
是否原地排序:是原地排序。