zoukankan      html  css  js  c++  java
  • CF1151F Sonya and Informatics(dp+矩阵快速幂)

    这题设计二维状态f[][]表示前i个里面有几个0,假设数列中总共有cnt个0最后答案就是操作k次后前i个里面有cnt个0/所有情况

    因为k十分巨大,所以考虑使用矩阵快速幂加速dp

    对于矩阵状态的设计,就是看看转移状态,发现转移状态只是一个常数,因此列出矩阵后做一遍快速幂即可

    #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=200;
    int pow_mod(int x,int i) {
        int res=1;
        while(i){
            if(i&1) res=(ll)res*x%mod;
            x=(ll)x*x%mod;
            i>>=1;
        }
        return res;
    }
    int n,k,a[N];
    int cnt;
    struct node{
        int a[N][N];
        node(){memset(a,0,sizeof(a));}
    }s,t;
    node operator *(node a,node b) {
        node tmp;
        for(int i=0;i<=cnt;i++) {
            for(int j=0;j<=cnt;j++) {
                for(int k=0;k<=cnt;k++) {
                    tmp.a[i][j]=((ll)tmp.a[i][j]+(ll)a.a[i][k]*b.a[k][j]%mod)%mod;
                }
            }
        }
        return tmp;
    }
    node matrix_pow(node a,int i) {
        node b;
        for(int i=0;i<=cnt;i++) b.a[i][i]=1;
        while(i) {
            if(i&1) b=b*a;
            a=a*a;
            i>>=1;
        }
        return b;
    }
    int main() {
        ios::sync_with_stdio(false);
        cin>>n>>k;
        for(int i=1;i<=n;i++)
            cin>>a[i],cnt+=(a[i]==0);
        int num=0;
        for(int i=1;i<=cnt;i++) num+=(a[i]==0);
        s.a[0][num]=1;
        for(int i=0;i<=cnt;i++) {
            if(i!=0) t.a[i-1][i]=1ll*(cnt-(i-1))*(cnt-(i-1))%mod;
            t.a[i][i]=1ll*(1ll*i*(cnt-i)%mod+1ll*(cnt-i)*(n-cnt-cnt+i))%mod;
            t.a[i][i]=(t.a[i][i]+1ll*cnt*(cnt-1)/2%mod)%mod;
            t.a[i][i]=(t.a[i][i]+1ll*(n-cnt)*(n-cnt-1)/2%mod)%mod;
            if(i!=cnt) t.a[i+1][i]=1ll*(i+1)*(n-cnt-cnt+i+1)%mod;
        }
        t=matrix_pow(t,k);
        s=s*t;
        int ans=s.a[0][cnt];
        int tot=0;
        for(int i=0;i<=cnt;i++)
            tot=((ll)tot+s.a[0][i])%mod;
        ans=((ll)ans*pow_mod(tot,mod-2))%mod;
        cout<<ans<<endl;
        return 0;
    }
    View Code
  • 相关阅读:
    LeetCode91 Decode Ways
    LeetCode93 Restore IP Addresses
    LeetCode92 Reverse Linked List II
    LeetCode90 Subsets II
    LeetCode89 Gray Code
    最长公共子序列及其引申问题
    constexpr:编译期与运行期之间的神秘关键字
    I/O模型: 阻塞、非阻塞、I/O复用、同步、异步
    LeetCode86 Partition List
    maven 安装 过程
  • 原文地址:https://www.cnblogs.com/ctyakwf/p/13445120.html
Copyright © 2011-2022 走看看