题目大意:求$fib(2^n)$
就是求fib矩阵的(2^n)次方%p,p是质数,根据费马小定理有
注意因为模数比较大会爆LL,得写快速乘法...
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
#include<bits/stdc++.h> #define ll long long #define MOD(x) ((x)>=mod?(x-mod):(x)) using namespace std; const int maxn=500010; const ll mod=1125899839733759; struct mtx{ll mp[2][2];mtx(){memset(mp, 0, sizeof(mp));}}ans, base; ll n, T; inline ll mul(ll a, ll b, ll mod) { ll ans=0; a%=mod; for(;b;b>>=1, a=MOD(a+a)) if(b&1) ans=MOD(ans+a); return ans; } mtx operator*(mtx a, mtx b) { mtx c; for(int i=0;i<2;i++) for(int j=0;j<2;j++) for(int k=0;k<2;k++) c.mp[i][j]=MOD(c.mp[i][j]+mul(a.mp[i][k], b.mp[k][j], mod)); return c; } inline ll power(ll a, ll b, ll mod) { ll ans=1; for(;b;b>>=1, a=mul(a, a, mod)) if(b&1) ans=mul(ans, a, mod); return ans; } inline ll mtx_power(ll b) { if(!b) return 0; for(;b;b>>=1, base=base*base) if(b&1) ans=ans*base; return ans.mp[1][0]; } int main() { scanf("%lld", &T); while(T--) { scanf("%lld", &n); ll t=power(2, n, mod-1); base.mp[0][0]=base.mp[0][1]=base.mp[1][0]=1; base.mp[1][1]=0; ans.mp[0][0]=ans.mp[1][1]=1; ans.mp[1][0]=ans.mp[0][1]=0; printf("%lld\n", mtx_power(t)); } }