算法性能评估
排序
希尔排序
public static void shellSort(int[] arr){
//不断地缩小增量
for (int interval =arr.length/2;interval >0;interval=interval/2){
//增量为1的插入排序
for (int i=interval;i<arr.length;i++){
int target=arr[i];
int j=i-interval;
while (j>-1&&target<arr[j]){
arr[j+interval]=arr[j];
j-=interval;
}
arr[j+interval]=target;
}
}
}
如何评估一个算法的性能?
评估算法性能,主要评估问题的输入规模n与元素的访问次数。f(n)的关系。规模越大,访问的总次数也越多。整体成上升的状态,但有的快有的慢。
大O表示法
大O符号,需要忽略非主体部分:如常数项、低阶项。只保留主体的部分,其余部分不需要。大O,表示这个算法的一个上界。算法的运行时间f(n)趋近并小于等于这个O(g(n)).总是贴近但是不超过O(g(n))。
如何计算
1、找到一个基本操作(最深层循环)
一层的循环:复杂度为O(n):线性复杂度
双层的循环:n*n:故复杂度为n的平方:平方复杂度
常数阶的算法:无论N怎么增长,所花的时间一直都是固定的时间。无论规模怎么扩大,我的计算还是常数阶的表示为O1.
2、分析该基本操作的执行次数x与问题规模n的关系x=f(n)
3、x的数量级O(x)就是算法时间复杂度T(n)
举例
常用技巧
1、加法法则:O(f(n))+O(g(n))=O(max(f(n),g(n)))
2、乘法法则:O(f(n))×O(g(n))=O(f(n)×g(n))
由上图可以看出来,在规模增加一些的时候,每一种函数需要的时间变化的趋势不同,相应的性能也就不同了。所以最好的是O(1)。
降低复杂度的一个层次,效率可以提升很多
三种复杂度
最坏时间复杂度:考虑输入数据“最坏”的情况
平均时间复杂度:考虑所有输入数据都等概率出现的情况
最好时间复杂度:考虑输入数据“最好”的情况