对于这一类转移次数很多的,肯定是考虑矩阵快速幂比较有效
对于状态设计,就是把有用的状态和常数放到状态矩阵中
然后构造出转移矩阵,对于本题因为p/n的答案不定,所以考虑整除分块后,分块求取答案
#include<bits/stdc++.h> #define getsz(p) (p?p->sz:0) using namespace std; typedef long long ll; const int mod=1e9+7; const int N=3e5+10; struct node{ ll a[5][5]; node(){ memset(a,0,sizeof a); } }s; node operator *(node a,node b){ node tmp; for(int i=0;i<3;i++){ for(int j=0;j<3;j++){ for(int k=0;k<3;k++) tmp.a[i][j]=(tmp.a[i][j]+a.a[i][k]*b.a[k][j]%mod)%mod; } } return tmp; } node martixpow(node x,int k){ node tmp; for(int i=0;i<3;i++){ tmp.a[i][i]=1; } while(k){ if(k&1){ tmp=tmp*x; } k>>=1; x=x*x; } return tmp; } int main(){ ios::sync_with_stdio(false); int t; cin>>t; while(t--){ ll a,b,c,d,p,n; cin>>a>>b>>c>>d>>p>>n; if(n==1){ cout<<a<<endl; continue; } else if(n==2){ cout<<b<<endl; continue; } int r; for(int i=3;i<=n;){ int tmp=p/i; if(tmp==0) r=n; else{ r=min(n,p/tmp); } node t; t.a[0][0]=d,t.a[0][1]=c,t.a[0][2]=tmp; t.a[1][0]=1,t.a[2][2]=1; t=martixpow(t,r-i+1); int tmpb=(t.a[0][0]*b+t.a[0][1]*a+t.a[0][2])%mod; int tmpa=(t.a[1][0]*b+t.a[1][1]*a+t.a[1][2])%mod; a=tmpa; b=tmpb; i=r+1; } cout<<b<<endl; } return 0; }