前言
努力是为了不平庸~
算法学习有些时候是枯燥的,这一次,让我们先人一步,趣学算法!
1、对兔子数列算法的优化
接着上一章所说这样子一个爆炸增量级的算法显然是不可取的,书中第一次优化的代码是使用的动态规划的思想,不过并没有提及,因为比较简单,不用动态规划也可以讲通
int Fib2(int n){
int*F=new int[n+1];//定义一个长度为n+1的数组,空间尚未使用F[1]=1;
F[2]=1;
for(int i=3;i<=n;i++)
F[i]=F[i-1]+F[i-2];return F[n];
}
但事实上来讲我们并不需要这长度为n的空间,直接在每次遍历中迭代数据就不用要额外空间存放每一年的兔子数量:
int Fib3( int n){
if(n==1l|n==2)
return 1;
int s1=1; l/用s1和s2记录前面的两项int s2=1;
for(int i=3;i<=n;i++){
int tmp=s1+s2;s1=s2;
s2=tmp ;
}
return s2;
}
这样子写下来复杂度就从O(2^n)降到了O(n)
说到这我就插点题外话,在今年我打了蓝桥杯,其中pythonB组的国赛第一题就是这样一个斐波拉契数列的题,我就是用的迭代但是根本跑不完数据,我在这里把题目发出来,大家可以思考一番。
在这贴一下别人gitte里的AC代码,如果感兴趣也可以查看一番https://gitee.com/ayoyo/Algorithm/blob/%E8%93%9D%E6%A1%A5%E6%9D%AF%E5%9B%BD%E8%B5%9B/A.py
除此外书中提及了一句斐波拉契数列O(logn)复杂度的算法,然后我就查阅了一番资料,确实收获颇多,因为之前从未想过这样子的套路。
2、我们应当怎样高效学习算法
这个问题其实在我的一篇文章中我已经总结过了,那一篇文章详细记录了我上学期从零开始至今学习算法的经历与经验。。
首先我认为刷题要分精刷和粗刷,当然前提是这个题你做不出来
我认为经典的题,例如买卖股票、最长公共子序列这些top100题是可以精刷的, 那么怎么算精刷呢,我认为五遍刷题法就是所谓精刷
当然五遍只是说说,三遍四遍都行的嘿嘿 那前提自然是你已经可以将每一行代码他的含义,在整个程序中的作用给自己讲一遍,讲清楚。
那就证明你吃透了。那其他题就可以粗刷,粗刷是为了提升自己的题感,提升自己的思维,往往其实有很多题,
比如动态规划的题,你只有通过不断的去刷dp题,提升题感,下一次你才知道这一个题可以用背包模型,可以用线性动态规划。
又或者像那种偏脑经急转弯类的,就是那个点想不到你就做不出,想到就轻而易举,这种题粗刷就能提升自己思维。
还有就是我认为每日一题其实也是比较有必要的,其作用我认为是来检验你的缺陷的,这种随机性的题往往可以检测出我们有哪些不足,应该去弥补。
在这个暑假我也坚持了每日一题,就发现我有一很薄弱的地方,那就是位运算,哪怕是easy的位运算,很多我都是一筹莫展的。
虽然我现在算法水平仍然是个菜鸟,但是每天多做一天,完全吸收它,那么一年后就完全吸收了365题,总归是有进步的,但是如果放弃了,那算法水平真的就是会飞速下降。
Donald Ervin Knuth说:“程序就是蓝色的诗”。而这首诗的灵魂就是算法,走进算法,你会发现无与伦比的美!
持之以恒地学习,没有什么是学不会的。行动起来,没有什么不可以!