矩阵快速幂
https://ac.nowcoder.com/acm/problem/19115
#include<bits/stdc++.h> #define fi first #define se second #define INF 0x3f3f3f3f #define fio ios::sync_with_stdio(false);cin.tie(0);cout.tie(0) #define pqueue priority_queue #define NEW(a,b) memset(a,b,sizeof(a)) const double pi=4.0*atan(1.0); const double e=exp(1.0); const int maxn=1e6+8; typedef long long LL; typedef unsigned long long ULL; const LL mod=10007; using namespace std; int dp[maxn]; int di[3]; struct maxt{ int s[3][3]; int ii,jj; }t,x; maxt MUL(maxt a,maxt b){ int kk=a.jj; maxt ans; ans.ii=a.ii; ans.jj=b.jj; for(int i=1;i<=a.ii;i++){ for(int j=1;j<=b.jj;j++){ ans.s[i][j]=0; for(int k=1;k<=kk;k++){ ans.s[i][j]+=a.s[i][k]*b.s[k][j]; } ans.s[i][j]%=mod; } } return ans; } maxt mqpow(maxt x,LL u){ maxt ans; ans.ii=x.ii; ans.jj=x.jj; for(int i=1;i<=ans.ii;i++){ for(int j=1;j<=ans.jj;j++){ if(i==j){ ans.s[i][j]=1; } else{ ans.s[i][j]=0; } } } while(u){ if(u&1){ ans=MUL(ans,x); } x=MUL(x,x); u>>=1; } return ans; } LL qpow(LL a,LL b){ LL ans=1; while(b){ if(b&1){ ans=ans*a%mod; } a=a*a%mod; b>>=1; } return ans; } int main(){ int n,k; cin>>n>>k; dp[1]=k; di[1]=0; di[0]=k; t.ii=t.jj=2; t.s[1][1]=k-2; t.s[1][2]=k-1; t.s[2][1]=1; t.s[2][2]=0; x.s[2][1]=0; x.s[1][1]=k*(k-1)%mod; x.ii=2; x.jj=1; maxt g=mqpow(t,n-2); g=MUL(g,x); int dii=g.s[2][1]; int dpp=dp[1]*qpow(k-1,n-1)%mod; int ans=dpp-dii; ans%=mod; if(ans<0) ans+=mod; cout<<ans<<endl; }