A Short problem
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 852 Accepted Submission(s): 335
Problem Description
According to a research, VIM users tend to have shorter fingers, compared with Emacs users.
Hence they prefer problems short, too. Here is a short one:
Given n (1 <= n <= 10 18), You should solve for
g(g(g(n))) mod 10
9 + 7
where
g(n) = 3g(n - 1) + g(n - 2)
g(1) = 1
g(0) = 0
Hence they prefer problems short, too. Here is a short one:
Given n (1 <= n <= 10 18), You should solve for
where
Input
There are several test cases. For each test case there is an integer n in a single line.
Please process until EOF (End Of File).
Please process until EOF (End Of File).
Output
For each test case, please print a single line with a integer, the corresponding answer to this case.
Sample Input
0 1 2
Sample Output
0 1 42837
Source
代码:
#include<cstdio>
#define ll __int64
int mod;
struct Matrix
{
ll m[2][2];
void init()
{
m[0][0]=3;m[0][1]=1;
m[1][0]=1;m[1][1]=0;
}
}a;
Matrix mul(Matrix a,Matrix b)
{
Matrix c;
int i,j,k;
for(i=0;i<2;i++)for(j=0;j<2;j++)
{
c.m[i][j]=0;
for(k=0;k<2;k++)
c.m[i][j]=(a.m[i][k]*b.m[k][j]%mod+c.m[i][j])%mod;
}
return c;
}
Matrix mpow(Matrix a,ll n)
{
Matrix c;
int i,j;
for(i=0;i<2;i++)for(j=0;j<2;j++)c.m[i][j]=(i==j);
for(;n;n>>=1)
{
if(n&1)c=mul(c,a);
a=mul(a,a);
}
return c;
}
ll solve(ll n,ll m)
{
a.init();
mod=m;
a=mpow(a,n);
return a.m[0][1];
}
int main()
{
ll n;
while(~scanf("%I64d",&n))
printf("%I64d\n",solve(solve(solve(n,183120),222222224),1000000007));
return 0;
}
本文讨论了如何高效解决复杂递归序列求模问题,通过矩阵快速幂技巧优化计算过程,适用于需要频繁求解特定序列模运算的场景。
304

被折叠的 条评论
为什么被折叠?



