题面:
思路:
看一眼这个公式:
$x\left[n+1\right]=\left(a\ast x\left[n\right]+c\right) mod m$
递推,数据范围$n\leq 10^18$,自然想到矩阵快速幂
构造如下矩阵:
状态矩阵:
$\begin{bmatrix}x\lbrack i\rbrack&1\end{bmatrix}$
转移矩阵:
$\begin{bmatrix}a&0\\c&1\end{bmatrix}$
从x[0]开始做转移矩阵的n次幂,再乘上状态矩阵即可
Code:
1 // luogu-judger-enable-o2 2 #include<iostream> 3 #include<cstdio> 4 #include<cstring> 5 #include<algorithm> 6 #define ll long long 7 using namespace std; 8 inline ll read(){ 9 ll re=0,flag=1;char ch=getchar(); 10 while(ch>‘9‘||ch<‘0‘){ 11 if(ch==‘-‘) flag=-1; 12 ch=getchar(); 13 } 14 while(ch>=‘0‘&&ch<=‘9‘) re=(re<<1)+(re<<3)+ch-‘0‘,ch=getchar(); 15 return re*flag; 16 } 17 ll n,m,A,C,st,g; 18 ll mul(ll l,ll r){ 19 ll re=0;if(l<r) swap(l,r); 20 while(r){ 21 if(r&1ll) re=(re+l)%m; 22 r>>=1ll;l=(l+l)%m; 23 } 24 return re; 25 } 26 struct ma{ 27 ll a[10][10],n,m; 28 ma(){memset(a,0,sizeof(a));n=m=0;} 29 void clear(){memset(a,0,sizeof(a));n=m=0;} 30 const void operator =(const ma &b){ 31 n=b.n;m=b.m;ll i,j; 32 for(i=1;i<=n;i++) for(j=1;j<=n;j++) a[i][j]=b.a[i][j]; 33 } 34 }a,b; 35 ma mmul(ma x,ma y){ 36 ma re;re.n=x.n;re.m=y.m;ll i,j,k; 37 for(i=1;i<=x.n;i++){ 38 for(j=1;j<=y.m;j++){ 39 for(k=1;k<=x.m;k++){ 40 re.a[i][j]+=mul(x.a[i][k],y.a[k][j]); 41 re.a[i][j]%=m; 42 } 43 } 44 } 45 return re; 46 } 47 ma ppow(ma x,ma y,ll t){ 48 while(t){ 49 if(t&1ll) x=mmul(x,y); 50 y=mmul(y,y);t>>=1ll; 51 } 52 return x; 53 } 54 int main(){ 55 m=read();A=read();C=read();st=read();n=read();g=read(); 56 a.n=1;a.m=2;b.n=b.m=2; 57 a.a[1][1]=st;a.a[1][2]=1; 58 b.a[1][1]=A;b.a[2][1]=C;b.a[2][2]=1; 59 ma ans=ppow(a,b,n); 60 printf("%lld",ans.a[1][1]%g); 61 }