如何评价代码好坏

本文详细讲解了代码质量评估中的复杂度分析,包括大O表示法的应用,常见时间复杂度如O(n), O(1), O(n2), O(logn), O(nlogn)等的实例,以及空间复杂度的讨论。还涉及了最好、最坏和平均复杂度的概念,并通过实际案例解析复杂度曲线的影响。
摘要由CSDN通过智能技术生成

概念

  1. 数据结构
    数据结构是指一组数据的存储结构
  2. 算法
    操作数据的方法

复杂度分析

大O复杂度表示法

复杂度分析原则

1.最大循环原则
  在一个复杂度表达式中,低阶/常量/系数并不左右其增长趋势,故只需记录最大的一个量,例:T(n) = O(3n2+n+2)中,系数3低阶n和常量2可以省略不计,该表达式最终记为T(n) = O(n2)

2. 加法原则
  同样遵循最大循环原则只记录最大的一个量,例:T(n) = O(n2)+O(n)中,低阶n可以省略不计,该表达式最终记为T(n) = O(n2)

3. 乘法原则
  嵌套代码的复杂度等于内外层复杂度乘积,例:T(n) = O(n)*O(n),该表达式最终记为T(n) = O(n2)

时间复杂度

常见复杂度

  假设每行代码执行时间相同,粗略计算得出,例:

1.O(n)

public void run(int n){
  int sum = 0;
  for(int i = 1;i<n;i++){
    sum++;
  }
}

执行时间会随着数据规模n的增大而增大

2.O(1) 常量级复杂度

public void run(int n){
  int sum = 0;
  for(int i = 1;i<100;i++){
    sum++;
  }
}

执行时间并不会随着数据规模n的增大而增大

3.O(n2)

public void run(int n){
  int sum = 0;
  for(int i = 1;i<n;i++){
    for(int i = 1;i<n;i++){
      sum++;
    }
  }
}

4.O(log n)

public void run(int n){
  int sum = 0;
  int i = 1
  while(i<n){
    i = i * 2;
  }
}

循环第一次 21,第二次 22,第三次23,当 i = n的时候停止循环,故循环次数为log2n
5.O(n log n)

public void run(int n){
  int sum = 0;
  int i = 1
  for(int j = 1;j<n;j++){
    while(i<n){
      i = i * 2;
    }
  }
}
复杂度曲线

可以看到日常我们经常使用的多层循环一旦遇到大数据量,就会产生严重的后果
可以看到日常我们经常使用的多层循环一旦遇到大数据量,就会产生严重的后果!

空间复杂度

public void run(int n){
  //复杂度为O(1),因为无论数据量多大,都只开辟了一个空间
  int sum = 0;
  for(int i = 1;i<n;i++){
    sum++;
  }
  //复杂度为O(n)
  int[] sum = new int[n];
  for(int i = 1;i<n;i++){
    sum[i] = 1;//注意与赋值没有关系
  }
}

最好复杂度/最坏复杂度/平均复杂度

先看一段代码

public void run(){
  List list = new ArrayList<String>();
  list.add(1);
  list.add(2);
  list.add(3);
  list.add(4);
  list.add(5);
  int result = -1;
  for(int i = 0;i<list.size();i++){
    if(3==list.get(i)){
      result = list.get(i);
    }
  }
}

可以得出,该段代码时间复杂度为T(n) = O(n),接下来对代码进行优化,在找到要找的数字之后break,优化后的代码

public void run(){
  List list = new ArrayList<String>();
  list.add(1);
  list.add(2);
  list.add(3);
  list.add(4);
  list.add(5);
  int result = -1;
  for(int i = 0;i<list.size();i++){
    if(3==list.get(i)){
      result = list.get(i);
      break;
    }
  }
}

该代码最好的情况一次就找到并返回,最好复杂度为O(1)
该代码最坏的情况最后一次才找到,最坏复杂度为O(n+1),也就是O(n)
但一般情况下我们会使用平均复杂度去衡量,公式为:所有情况循环次数/所有情(包括要找的数不在集合中的情况), T ( n ) = 1 + 2 + 3 + . . . + n + n 1 + n = n 2 + 3 n 2 ( 1 + n ) T(n) =\frac{1+2+3+...+n+n}{1+n}=\frac{n^2+3n}{2(1+n)} T(n)=1+n1+2+3+...+n+n=2(1+n)n2+3n
但这种算法没有加上概率(因为在集合中和不在集合中概率相同),公式改为 T ( n ) = n 2 + 1 + 2 + 3 + . . . + n 2 n = 3 n + 1 4 T(n) =\frac{n}{2}+\frac{1+2+3+...+n}{2n}=\frac{3n+1}{4} T(n)=2n+2n1+2+3+...+n=43n+1可以看到这段代码的复杂度依旧为O(n)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值