如何分析、统计算法的执行效率和资源消耗
为什么需要复杂度分析
首先我们很多程序都可以通过统计,监控等方式帮助我们得到程序执行的时间与占用的内存大小。
但是这些统计方法有很大的局限性。
- 测试结果非常依赖测试环境。
不同的测试机器,同样的代码执行效率就不同。 - 测试结果数受数据规模的影响很大。
数据规模大,我们的代码执行效率低。测试结果不能真正的反应我们的内容
大O复杂度表示法
我们假设一行代码执行一次的时间是unit_time,那么总时间就可以进行计算循环N次,就是Nunit_time.
如果有双层循环,就是NNunit_time时间。总体时间就是NNunit_time +Nunit_time .总体来看时间与N成正比
T(N) = O(F(N))
N代表的是数据规模的大小,f(N)表示每行代码执行的次数综合。公式中的O表示执行时间T(N)和f(n)成正比。
大O时间复杂度并不具体表示代码真正的执行时间,而是表示代码执行时间岁数据规模增长的变化趋势。所以也叫作渐进时间复杂度。
时间复杂度分析
只关注循环执行次数最多的一段代码
在代码记录中如果其他代码执行量与最大的执行量级不在一个层面就可以直接忽略。只保留循环执行次数最多的一段代码即可。下面代码执行次数最多的就是循环,而且前面的执行次数不在一个量级,就直接忽略。
T(N) = O(N)
public void test(){
int i =1;
int b = 2;
int sum = 0 ;
for(int n =0 ; n <10000000000; n++){
sum+=i ;
}
}
加法法则:总复杂度等于量级最大的那段代码的复杂度
int cal(int n) {
int sum_1 = 0;
int p = 1;
for (; p < 100; ++p) {
sum_1 = sum_1 + p;
}
int sum_2 = 0;
int q = 1;
for (; q < n; ++q) {
sum_2 = sum_2 + q;
}
int sum_3 = 0;
int i = 1;
int j = 1;
for (; i <= n; ++i) {
j = 1;
for (; j <= n; ++j) {
sum_3 = sum_3 + i * j;
}
}
return sum_1 + sum_2 + sum_3;
}
结合这一段代码表示 第二循环与第三个循环 就类似我们上面所说的那两段代码执行效率 T(N) = O(N),
T(N) = O(F(NN )) 方法内容。其中无限大我们去最大的就是T(N) = O(F(NN ))
乘法法则
如果 T1(n)=O(f(n)),T2(n)=O(g(n));那么 T(n)=T1(n)T2(n)=O(f(n))O(g(n))=O(f(n)*g(n)).
常见的分析复杂度实例
案例图片粗略的分为两种,左侧:多项式量级和 右侧:非多项式量级。
随着数据规模的增长 ,非多项式量计算分执行时间或急剧增加。
以下是常见的几种 多项式时间复杂度
O(1)
只是一种常量级时间复杂度表啊是方法,并不是指一行代码。
只要代码执行时间不存n的增大而增长,那么时间复杂度都记为O(1)
O(logn)\O(nlogn)
logn 是根据代码循环执行了多少次 进行计算
nlogn 乘法法则, 循环执行了N遍 logn 的算法。
O(m+n)、O(m*n)
当我们在代码中有两个不知谁的量级大的循环时候,就需要将其都计算O(m+n)
空间复杂度分析
时间复杂度分析 表示渐进时间复杂度。
空间复杂度全称是渐进空间复杂度。表示算法的存储空间与数据规模的增长关系
网友评论