HDU 4549 M斐波那契数列 (矩阵快速幂+费马小定理)
2017-08-09 11:00
435 查看
思路:
通过列出几项我们就可以发现ab的指数是斐波那契数列。然后博主就开(智)心(障)的用矩阵快速幂算指数了。。却忘了一件事。。。谁说的取模对指数封闭的啊???md疯狂wa了六七次。
取模对乘法封闭但不意味着指数你可以直接取模啊。。
正解是根据费马小定理:
ab=cmodp
当 gcd(a,p)=1 并且p是素数的时候,有:ap−1=1modp 也就是说,指数上循环节为0 1 2 。。。。p-1,所以我们可以对指数模(1e9+7-1)。
好了,结果出来了。
#include <cstdio> #include <iostream> #include <string.h> #include <queue> #include <algorithm> typedef long long int lli; using namespace std; const int mod = 1000000007; const int n = 2; struct mat{ lli ma ; }; mat operator * (mat &a,mat &b){ mat c; const int mm = mod-1; memset(c.ma,0,sizeof(c.ma)); for(int k=0;k<n;++k){ for(int i=0;i<n;++i){ for(int j=0;j<n;++j){ c.ma[i][j] += a.ma[i][k]%mm*(b.ma[k][j]%mm)%mm; c.ma[i][j] %= mm; } } } return c; } mat qp(mat a,lli k){ mat c; for(int i=0;i<n;++i){ for(int j=0;j<n;++j){ c.ma[i][j] = (i==j); } } for(;k;k>>=1){ if(k&1) c=c*a; a = a*a; } return c; } lli qp(lli a,lli e577 x){ lli res = 1;a %= mod; for(;x;x>>=1){ if(x&1){ res *= a;res %= mod; } a = a*a%mod; } return res; } int main(){ int a,b,n; while(~scanf("%d%d%d",&a,&b,&n)){ mat zuo = {1,0, 0,0}; mat base = {1,1, 1,0}; if(n == 0){ printf("%d\n",a%mod); continue; } else{ base = qp(base,n-1); lli a1 = base.ma[0][1],b1 = base.ma[0][0]; lli ans = qp(a,a1)%mod; ans = (ans*qp(b,b1))%mod; printf("%lld\n",ans); } } }
相关文章推荐
- HDU 4549 M斐波那契数列(矩阵快速幂3)+费马小定理
- HDU 4549 M斐波那契数列(矩阵快速幂+费马小定理)
- hdu 4549 M斐波那契数列(快速幂 矩阵快速幂 费马小定理)
- HDU 4549 M斐波那契数列 (矩阵快速幂 + 费马小定理)
- HDU 4549 M斐波那契数列(矩阵快速幂+费马小定理)
- HDU - 4549 M斐波那契数列(矩阵快速幂+费马小定理)
- HDU 4549 M斐波那契数列(矩阵快速幂&费马小定理)
- HDU 4549 M斐波那契数列(矩阵快速幂+费马小定理)
- HDU 4549 M斐波那契数列 矩阵快速幂加费马小定理
- 【HDU - 4549 】M斐波那契数列 【矩阵快速幂+费马小定理降幂】
- HDU 4549 M斐波那契数列(矩阵快速幂+欧拉定理)
- 【矩阵快速幂】HDU 4549 : M斐波那契数列(矩阵嵌套)
- HDU 4549 矩阵快速幂 + 快速幂取模 + 费马小定理
- hdu 4549 M斐波那契数列(费马小定理 + 二分快速幂 + 矩阵快速幂)
- hdu 4549 M斐波那契数列 【矩阵+快速幂+欧拉定理】
- Hdu 4549 M斐波那契数列 (矩阵 费马小定理降幂)
- hdu-4549 M斐波那契数列【矩阵快速幂】
- HDU 4549M斐波那契数列(矩阵快速幂+费马小定理)
- HDU 4549 M斐波那契数列【矩阵快速幂】
- hdu 4549 M斐波那契数列(矩阵快速幂,快速幂降幂)