设f(x)是菲波那切数列中第x个数,求f(a^b)mod n的值。
首先我们要知道一个结论:斐波那契数列对n取余,它的余数列是有周期性的。这样对于一个很大的数,我们只需找出它在周期中处于第几个位置,然后找出相应的余数就行了。这样就把问题化为找斐波那契数列的余数列,和找出余数列的周期。
根据加法取余定理,我们只要在算出f[i]后直接f[i]=f[i] mod n即为对应的余数。周期只要判断第几个数余数为0而它的下一个数余数为1即可。
紫书上面对斐波那契数列的定义首先就写错了……看了好久
AC代码:
#include <iostream>
using namespace std;
typedef unsigned long long ULL;
const int maxn=1000010;
int f[maxn],kase;
int pow_mod(ULL a,ULL n,int m)
{
if(n==0) return 1;
ULL x=pow_mod(a,n/2,m);
ULL ans=(ULL)x*x%m;
if(n%2==1)
ans=ans*a%m;
return ans;
}
int solve(ULL a,ULL b,int n)
{
if(a==0||n==1) return 0;
for(int i=2;;i++)
{
f[i]=f[i-1]+f[i-2];
f[i]=f[i]%n;
if(f[i-1]==0&&f[i]==1)
{
kase=i-1;
break;
}
}
int v=pow_mod(a%kase,b,kase);
return f[v];
}
int main()
{
//cout<<pow_mod(3,4,5)<<endl;
int t,n;
ULL a,b;
cin>>t;
while(t--)
{
cin>>a>>b>>n;
f[0]=0;
f[1]=1;
cout<<solve(a,b,n)<<endl;
}
return 0;
}