今天看了寻找条件数这道题,发现这道题适用的技巧还是很巧妙的,首先一个技巧就是:思考的角度要改变,当正向计算量很大时,那么就反向考虑。题目中要求寻找最小的M,使得N*M的十进制结果,只包含1或者是0。但是如果正向寻找,那么会很慢,于是反向考虑,首先寻找十进制数中,只包含1和0的数,然后看能否被N整除。这样,问题就变成了一个十进制数能被N整除,那么这个数可以看成有一系列的数相加构成,而如果这些数对N的余数相加,能被N整除,那么这些数的和,也可以被N整除。这么一个很好的转换,就把问题解决了。复杂度从指数级,变为了(K-1)*N,其中K是指,当找到最小的M时,该M的位数。
在看书的过程中,可以看看其他的帖子,看看别人怎么分析,这样你看问题的角度会开一些,切记仅仅看一本书。
下面贴一些帖子,有助于理解:
http://www.cnblogs.com/pangxiaodong/archive/2011/09/30/2196177.html
http://blog.csdn.net/jcwkyl/article/details/3859155
http://blog.csdn.net/jcwKyl/article/details/3859155
另一道题边是练习递归算法,常用的斐波那契数列,这个问题看起来很简单,只要记得边界问题:n=0,返回0,n=1,返回1,F(n) = F(n-1) + F(n-2),那么就可以写程序了。
但是这个问题,会使得很多重复计算,这样便浪费大量的资源。
于是可以通过空间换时间,开辟一个数组,或者用两个数记录之前的计算结果,
int F[n];
F[0] = 0, F[1] = 1;
for(int i =2 ; i < n; i++){
F[i] = F[i-1]+F[i-2];
}
这样便实现了斐波那契额数列的计算,但是这还远远不行。
题目中,给出了使用矩阵计算的方法,比如[F(n) F(n-1)] = [F(n-1) F(n-2) * A,其中A = [[1 0]; [ 1 1]],这样当n取定一个值后,便可以通过计算矩阵A的n次幂,便可以计算。但是如何高效的计算A的n次幂,可以将n进行二项式分解,系数时0或者是1,其余的就是2次,这样可以通过分解,来加速计算矩阵乘方。最终完成计算。最终结论是,计算矩阵的幂是十分关键的,因此要专注点放在这个上,便可以完成这道题的计算。
贴几个博客,可以参考:
http://www.cnblogs.com/xiaoxxmu/p/5513469.html
http://blog.csdn.net/sunnyyoona/article/details/18727655
http://blog.csdn.net/linyunzju/article/details/7706896