算法的时间复杂度计算方法

  《大话数据结构》中对算法的时间复杂度定义如下:

  “算法分析时,语句的总执行次数T[n]是关于问题规模n的函数,进而分析T[n]随n的变化情况并确定T[n]的数量级。算法的时间复杂度,也就是算法的时间度量,记做T[n]=O(f[n]),表示随问题规模n的增大,算法的执行时间的增长率和f[n]的增长率相同,称做算法的渐进时间复杂度,简称时间复杂度,f[n]是问题规模n的某个函数。”

  根据定义举个例子,计算1+2+3+4+···+100 = ?

  int sum = 0 ,n=100;

  for(int i=1;i<=n;i++){

    sum+=i;

  }

  算法执行完毕时,语句的总执行次数T[n] = 1+n+1+n = 2n+2,随着问题规模n的增大,算法的执行时间的增长率和f[n]的增长率相同,其中f[n] = 2n,因为随着n的增大,常数2并不增大,为了简化计算,取主要的执行次数2n,这样的话T[n] = O(2n)。 也就是O(n) 【下文解释为什么去掉2】

  同一个问题,我们使用高斯的算法解决。

  int sum = 0,n = 100;

  sum = (n*(n+1))/2;

  算法执行完毕时,语句总执行次数为2,T[n]=O(2)。也就是O(1)【下文解释】

  通过以上例子,给出“大O阶”的推倒(ノ*・ω・)ノ 步骤:

  1.计算语句总执行次数得出f[n]

  2.用常数1取代运行此书中的所有加法常数

  3.在修改后的运行次数函数中,只保留最高阶项

  4.如果最高阶项存在且不是1,去除于这个项相乘的常数

  再举个例子

  int n=100; 

  for(int i=0; i<n; i++){

    for(int j=0; j<n; j++){

      n--;

    }

  }

  printf("n=%d",n);

  第一句很明显执行1次,嵌套循环的执行次数一眼看不出来,这就需要分析了,先看内循环,j自增一次,n自减一次,可以推测当n自减到n/2时,第一次内循环结束,此时第二句执行了一次。接下来看第二次内循环,当n减到n/4的时候,第二次内循环结束,第二句执行了第二次。由此可知,当i>=n/(2i)时,外循环也就是第二句结束,也就是说外循环最多运行n/(2i)次,当n等于一百万的时候,i等于16,所以外循环可以忽略不计,内循环 n--; 执行了n-n/(2i)次,约等于n次。所以这个例子的算法时间复杂度为O(n)。

  上面那个例子是我自己编的。最开始计算外层循环的时候也迷糊了,在群里和大家讨论了才明白,这也告诉我们,计算复杂度的时候,一定要有全局观,不要死磕每一句的执行次数。今早在看《编程珠玑》时,了解了近似估算,发现也可以用在这个地方。

  最后给出各种复杂度的图像,绘图工具使用的是Mathematica,感觉是比Matlab更好用的数学工具。

  

         

  删除几个增长率快的

  

 

转载于:https://www.cnblogs.com/Thkeer/p/5428195.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值