answer
First, consider the $ N \ leq 10 ^ 5 $
It is easy to think of dynamic programming
We can easily state design
$ F_ {i, j} $ represents the number of programs
$ I $ has been determined that the current position $ i $
J represents $ $ $ j-m + 1 ~ j $ binary states
And state transition equation
$ F_ {i, j} = \ Sigma {f_ {i-1, k}} (k, j k are legitimate and the access is the one J) $
So we just need to pre-whether all states can convert between various legal and state, and then to dynamic programming
1 #include<bits/stdc++.h> 2 using namespace std; 3 typedef long long LL; 4 const int MOD=1e9+7,MAXN=1e5+50,MAXM=8,MAXP=70; 5 inline void add(int &x,int y){ 6 x=(x+y)%MOD; 7 } 8 LL N; 9 int M,K; 10 bool bin[MAXM],leg[MAXP]/*״̬ÊÇ·ñºÏ·¨*/,tran[MAXP][MAXP]/*תÒÆÊÇ·ñºÏ·¨*/; 11 inline void sign(){ 12 int cur=0,nxt=0,sum[MAXM]={0}; 13 for(int i=1;i<=M;i++) 14 cur=cur<<1|bin[i]; 15 for(int i=2;i<=M+1;i++) 16 nxt=nxt<<1|bin[i]; 17 for(int i=1;i<=M+1;i++) 18 sum[i]=sum[i-1]+bin[i]; 19 if(sum[M]>K||sum[M+1]-sum[1]>K) 20 return; 21 leg[cur]=leg[nxt]=1; 22 tran[cur][nxt]=1; 23 } 24 void dfs(int x){/*ö¾Ù²¢±ê¼ÇËùÓкϷ¨µÄ״̬*/ 25 if(x==M+2){ 26 sign(); 27 return; 28 } 29 bin[x]=0; 30 dfs(x+1); 31 bin[x]=1; 32 dfs(x+1); 33 } 34 int f[MAXN][MAXP],maxp,ans; 35 inline void dp(int S){/*Çó½â´ÓÌض¨×´Ì¬³ö·¢µÄ·½°¸Êý*/ 36 memset(f,0,sizeof(f)); 37 f[M][S]=1; 38 for(int i=M+1;i<=M+N;i++) 39 for(int j=0;j<maxp;j++) 40 for(int k=0;k<maxp;k++) 41 if(tran[j][k])/*´æÔÚjµ½kµÄתÒÆ*/ 42 add(f[i][j],f[i-1][k]); 43 add(ans,f[N+M][S]); 44 } 45 int main(){ 46 scanf("%lld%d%d",&N,&M,&K); 47 dfs(1); 48 maxp=1<<M; 49 for(int i=0;i<maxp;i++) 50 if(leg[i]) 51 dp(i); 52 printf("%d",ans); 53 return 0; 54 }
Then consider $ N \ leq 10 ^ {15} $
We observed that pretreatment of the adjacency matrix (whether each state transition between the matrix), can be found which is actually a transfer problem closure (similar to the Floyd), each state will be pressing the matrix operation N times
It is possible to use fast power optimization matrix, the code is very simple
1 #include<bits/stdc++.h> 2 using namespace std; 3 typedef long long LL; 4 const int MOD=1e9+7,MAXN=1e5+50,MAXM=8,MAXP=70; 5 inline void add(LL &x,LL y){ 6 x=(x+y)%MOD; 7 } 8 LL N,maxp,ans,M,K; 9 bool bin[MAXM],leg[MAXP]; 10 struct matrix{ 11 LL a[MAXP][MAXP]; 12 matrix (){ 13 memset(a,0,sizeof(a)); 14 } 15 friend matrix operator*(matrix x,matrix y){ 16 matrix ret; 17 for(int i=0;i<maxp;i++) 18 for(int j=0;j<maxp;j++) 19 for(int k=0;k<maxp;k++) 20 add(ret.a[i][j],x.a[i][k]*y.a[k][j]); 21 return ret; 22 } 23 }tran,a; 24 inline void sign(){ 25 int cur=0,nxt=0,sum[MAXM]={0}; 26 for(int i=1;i<=M;i++) 27 cur=cur<<1|bin[i]; 28 for(int i=2;i<=M+1;i++) 29 nxt=nxt<<1|bin[i]; 30 for(int i=1;i<=M+1;i++) 31 sum[i]=sum[i-1]+bin[i]; 32 if(sum[M]>K||sum[M+1]-sum[1]>K) 33 return; 34 leg[cur]=leg[nxt]=1; 35 tran.a[cur][nxt]=1; 36 } 37 void dfs(int x){ 38 if(x==M+2){ 39 sign(); 40 return; 41 } 42 bin[x]=0; 43 dfs(x+1); 44 bin[x]=1; 45 dfs(x+1); 46 } 47 inline matrix pow(matrix x,LL y){ 48 matrix ret=x; 49 y--; 50 while(y){ 51 if(y&1){ 52 ret=ret*x; 53 } 54 x=x*x; 55 y>>=1; 56 } 57 return ret; 58 } 59 int main(){ 60 scanf("%lld%lld%lld",&N,&M,&K); 61 maxp=1<<M; 62 dfs(1); 63 a=pow(tran,N); 64 for(int i=0;i<maxp;i++) 65 if(leg[i]) 66 add(ans,a.a[i][i]); 67 printf("%lld",ans); 68 return 0 ; 69 }