1 条题解

  • 1
    @ 2022-7-14 19:54:19
    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    #define LL long long
    LL n,m,k,lim,mod=1000000007,ans;
    struct node{LL t[64][64];}re,x;
    int ok[64],bin[6];//ok:是否是合法状态
    void work(int zt,int num) {//计算初始合法转移
        ok[zt]=1;int kl=zt>>1;
        x.t[kl][zt]=1;
        if(num==k&&!(zt&1)) return;
        x.t[kl+bin[m]][zt]=1;
    }
    void dfs(int x,int num,int zt) {
        if(x==m+1) {work(zt,num);return;}
        dfs(x+1,num,zt);
        if(num<k) dfs(x+1,num+1,zt|bin[x]);
    }
    node operator * (node a,node b) {
        int i,j,k;node c;
        for(i=0;i<=lim;++i)
            for(j=0;j<=lim;++j) {
            c.t[i][j]=0;
            for(k=0;k<=lim;++k)
                c.t[i][j]+=a.t[i][k]*b.t[k][j]%mod,c.t[i][j]%=mod;
        }
        return c;
    }
    void ksm() {//快速幂
        int bj=0;
        while(n) {
            if(n&1) {
                if(!bj) re=x,bj=1;
                else re=re*x;
            }
            x=x*x;n>>=1;
        }
    }
    int main()
    {
        bin[1]=1;for(int i=2;i<=5;++i) bin[i]=bin[i-1]<<1;
        scanf("%lld%lld%lld",&n,&m,&k);
        lim=(1<<m)-1;dfs(1,0,0);ksm();
        for(int i=0;i<=lim;++i) if(ok[i]) ans+=re.t[i][i],ans%=mod;//答案统计
        printf("%lld",ans);
        return 0;
    }
    
    • 1

    信息

    ID
    358
    时间
    1000ms
    内存
    125MiB
    难度
    5
    标签
    递交数
    4
    已通过
    4
    上传者