排序算法学习过程的笔记总结,如有错误,望指正!
排序算法
排序也称排序算法(Sort Algorithm),排序是将一组数据,依指定的顺序进行排列的过程。
排序分类
1)内部排序:指将需要处理的所有数据都加载到内部存储器(内存)中进行排序。
2)外部排序法:
数据量过大,无法全部加载到内存中,需要借助外部存储(文件等)进行排序。
3)常见排序算法
算法时间复杂度
时间复杂度
1)一般情况下,算法中的基本操作语句的重复执行次数是问题规模n的某个函数,用T(n)表示,若有某个辅助函数(fn),使得当n趋近于无穷大时,T(n)/ f(n)的极限值为不等于零的常数,则称f(n)是T(n)的同数量级函数。记作T(n)=O ( f(n)),称O( f(n))为算法的渐进时间复杂度,简称时间复杂度。
2)T(n)不同,但时间复杂度可能相同。如:T(n)=n2+7n+6 与T(n)=3n2+2n+2它们的T(n)不同,但时间复杂度相同,都为O(n2)。
3)计算时间复杂度的方法:
-
用常数1代替运行时间中的所有加法常数T(n)=n2+7n+6=→> T(n)=n2+7n+1
-
修改后的运行次数函数中,只保留最高阶项T(n)=n2+7n+1 => T(n)= n2
-
去除最高阶项的系数T(n)=n2=> T(n)= n2=> O(n2 )
常见的时间复杂度
-
- 常数阶:O(1)
- 对数阶:O(log2n)
-
- 线性阶:O(n)
- 线性对数阶:O(nlog2n)
-
- 平方阶:O(n2)
- 立方阶:O(n3)
-
- k次方阶:O(nk)
- 指数阶:O(2n)
平均时间复杂度和最坏时间复杂度
-
平均时间复杂度是指所有可能的输入实例均以等概率出现的情况下,该算法的运行时间
-
最坏情况下的时间复杂度称最坏时间复杂度。通常时间复杂度均是最坏情况下的时间复杂度
-
平均时间复杂度和最坏时间复杂度是否一致,和算法有关(如图:)
算法空间复杂度
基本介绍
1)算法的空间复杂度(Space Complexity)即该算法所耗费的存储空间,它也是问题规模n的函数。
2)空间复杂度(Space Complexity)是对一个算法在运行过程中临时占用存储空间大小的量度。有的算法需要占用的临时工作单元数与解决问题的规模n有关,它随着n的增大而增大,当n较大时,将占用较多的存储单元,如快速排序和归并排序算法,基数排序就属于这种情况
3)算法分析时,主要讨论的是时间复杂度。看重的程序执行的速度。一些缓存产品(redis, memcache)和算法(基数排序)本质就是用空间换时间。
1. 冒泡排序
1.1 算法思想
冒泡排序(Bubble Sorting)基本思想:通过对待排序序列从前向后(从下标较小的元素开始) ,依次比较相邻元素的值,若发现逆序则交换,使数值较大的元素逐渐从前移向后部。
优化:排序的过程中,各元素不断接近自己的位置,如果一趟比较下来没有进行过交换,就说明序列有序,在排序过程中设置一个标志flag判断元素是否进行过交换,从而减少不必要的比较。
1.2 算法图解
图解分析:
(1)一共进行数组的大小-1次大的循环
(2)每一趟排序的次数在逐渐的减少
(3)如果某趟排序中,没有发生一次交换,可以提前结束冒泡排序。(优化)
1.3 代码实现
public static void bubbleSort(int[] arr){
int temp =0; //临时变量
boolean flag=false; //标识变量,表示是否进行过交换
for (int i=0; i <arr.length-1;i++){
for (int j=0; j<arr.length-1-i;j++){
//前面的数值大于后面的值则交换
if (arr[j] >arr[j+1]){
flag=true;
temp=arr[j];
arr[j]=arr[j+1];
arr[j+1]=temp;
}
}
if (!flag){
break;
}else {
flag=true;
}
}
}
2. 选择排序
2.1 算法思想
选择排序(select sorting)也是一种简单的排序方法。它的基本思想是:第一次从arr[0]arr[n-1]中选取最小值,与arr[0]交换,第二次从arr[1]arr[n-1]中选取最小值,与arr[1]交换,第三次从arr[2]~arr[n-1]中选取最小值,与 amr[2]交换,…,第i次从 arr[i-l]~arr[n-1]中选取最小值,与 arr[i-1]交换,…第n-1 次从arr[n-2]~arr[n-1]中选取最小值,与arr[n-2]交换,总共通过n-1次,得到一个按排序码从小到大排列的有序序列。
2.2 算法图解
以下图为例进行图解分析
过程分析:
-
选择排序一共有数组大小-1轮排序
-
每轮排序又是一次循环
-
- 先假定当前这个数是最小数
- 然后和后面的数值比较,若发现更小的数,则重新确定最小数,并得到下标
-
- 遍历到数组最后时,得到本轮最小数和下标
- 交换
2.3 代码实现
public static void selectSort(int[] arr){
for (int i=0; i<arr.