题目:输入一个正整数 n 求:1+2!+3!+...+n!
直观的思维就是遍历1...n,分别计算各个数的阶乘,然后求和,算法实现为:
public static long getSum(int n){
if(n >0) {//错误数据判断
int i,k,fac,sum=0; for(i=1;i<=n;i++){//遍历1...n fac=1; for(k=1;k<=i;k++)//求阶乘并累加 fac=fac*k; sum=sum+fac; } return sum; }else{ return -1; } }
但是只要稍微分析便可以发现2! = 2*1!,3! = 3*2! ...n! = n*(n-1)! ,上面的算法算然达到解决问题的目的,但是每一步的计算结果没有被充分利用,反而多次重复计算,导致了算法的时间复杂度及其大,按我们现在的这个分析去改善算法,关键就是在内层循环中,下一次循环要利用上一次循环计算的结果,自然的我们会想到需要一个变量去保存这个迭代中间值,用来改善下次迭代,设计算法如下:
public static long getSumByMySelf(int n){ long before = 1;//迭代中间值记录器 if(n>0){ long answer = 0 ; for(int index = 1 ; index <= n ; index ++){ before *= index;//更新迭代中间值 answer += before ;//累加本次循环的迭代结果 } return answer; }else{ return -1; } }
在mian方法中测试:
请输入一个正整数 5 直接思维计算结果153 改方法计算结果:153
计算结果是一样的,但是改进后的方法,保存上一次的迭代结果用于下一次迭代,使得每个数的阶乘运算都变成了一个乘法运算,时间复杂度大幅度降低,而牺牲的空间复杂读仅仅是需要定义一个基本变量来存储迭代的中间值。