您的位置:首页 > 其它

快速幂讲解

2016-08-16 12:22 85 查看
快速幂取模

用法:用于求解 a 的 b 次方,而b是一个非常大的数,用O(n)的复杂度会超时。那么就需要这个算法,注意它不但可以对数求次幂,而且可用于矩阵快速幂。

假如求 x ^ n 次方

我们可以把 n 表示为 2^k1 + 2k2 + 2^k3….,可以证明所有数都可以用前式来表示。(其实就是二进制表示数的原理)

那么 x^n = x^2^k1 * x^2^k2 * x^2^k3……

那么就可以利用二进制来加快计算速度了。

假如 x^23 , 23转化为二进制为 10111, 即 x^23 = (x^16) * ( x^4) * ( x^2) * (x^1);

通过判断二进制x是否为1来判断是否加入运算中,(x>>1)每次向右移动一位,(x&1)判断是否为1,如果是1,则加入运算。如果不是,则x的幂次方继续乘方(1,2,4,8,16,32增长,作为待用乘法因子)。

那么是不是可以在O(logn)的复杂度求解。

代码:

#include<iostream>
#include<cstdio>
using namespace std;
int pw(int a,int n)
{
int tmp=a,ans=1;
while(n)//这里用a的1次方来试,就很容易写出
{
if(n&1)
{
ans*=tmp;
}
tmp*=tmp;
n>>=1;
}
return ans;
}
int main()
{
int a,n;
cin>>a>>n;
cout<<pw(a,n)<<endl;
}


那么假如让你求一个矩阵的很大的次方幂呢,当然我们同样可以求解。

比如我们都知道斐波那契数列可以用矩阵来求

当求第非常大的一个斐波那契数的后几位时我们可以用上面方法求解了。

方法和上面的方法一模一样,只是把数 x 变成了一个矩阵。

注意代码中矩阵的存法,很好用,题目链接:http://acm.nyist.net/JudgeOnline/problem.php?pid=148

那么假如让你求一个矩阵的很大的次方幂呢,当然我们同样可以求解。

比如我们都知道斐波那契数列可以用矩阵来求

当求第非常大的一个斐波那契数的后几位时我们可以用上面方法求解了。

方法和上面的方法一模一样,只是把数 x 变成了一个矩阵。

注意代码中矩阵的存法,很好用,题目链接:http://acm.nyist.net/JudgeOnline/problem.php?pid=148
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: