zoukankan      html  css  js  c++  java
  • [HDU-6854] Kcats (2020多校7 T11) (笛卡尔树+区间dp)

    [HDU-6854] Kcats (2020多校7 T11) (笛卡尔树+区间dp)

    前缀(p_1,p_2,cdots,p_i)的单调栈大小,即(i)号节点在全局的笛卡尔树上对应的位置的所有在左边的祖先个数

    因此,区间(dp)笛卡尔树的树形,合并时,为了满足题目的限制,只需要记录左边的祖先个数(d)

    即定义(dp[l][r][d])为区间(l,r)对应笛卡尔树子树,且根节点左祖先个数为(d)的方案数

    合并两个子树时注意补上组合数,且自己这个点对于左儿子深度没有贡献

    #include<bits/stdc++.h>
    using namespace std;
    #define rep(i,a,b) for(int i=a,i##end=b;i<=i##end;++i)
    #define drep(i,a,b) for(int i=a,i##end=b;i>=i##end;--i)
    template <class T> inline void cmin(T &a,T b){ ((a>b)&&(a=b)); }
    template <class T> inline void cmax(T &a,T b){ ((a<b)&&(a=b)); }
    
    char IO;
    template <class T=int> T rd(){
        T s=0; int f=0;
        while(!isdigit(IO=getchar())) if(IO=='-') f=1;
        do s=(s<<1)+(s<<3)+(IO^'0');
        while(isdigit(IO=getchar()));
        return f?-s:s;
    }
    
    const int N=1e2+10,P=1e9+7;
    
    int n,a[N],C[N][N],dp[N][N][N];
    
    int main(){
        rep(i,0,N-1) rep(j,C[i][0]=1,i) C[i][j]=(C[i-1][j-1]+C[i-1][j])%P;
        rep(kase,1,rd()) {
            rep(i,1,n=rd()) a[i]=rd();
            memset(dp,0,sizeof dp);
            drep(i,n,1) rep(j,i,n) rep(k,i,j) 
                rep(d,~a[k]?a[k]:1,~a[k]?a[k]:n) 
                    dp[i][j][d]=(dp[i][j][d]+1ll*(i<k?dp[i][k-1][d]:1)*(k<j?dp[k+1][j][d+1]:1)%P*C[j-i][k-i])%P;
            printf("%d
    ",dp[1][n][1]);
        }
    }
    
    
    
    
    
  • 相关阅读:
    php实现求链表中倒数第k个节点
    在python正在使用mysql
    1002. 写这个号码 (20)(数学啊 ZJU_PAT)
    Lua 环境结构 --Linux
    Java程序猿JavaScript学习笔记(4——关闭/getter/setter)
    C/C++数据对齐汇总
    多线程
    11gRAC CHM 管理
    hdu 4059 The Boss on Mars(纳入和排除)
    模板方法模式分析、图表和基本代码
  • 原文地址:https://www.cnblogs.com/chasedeath/p/13485478.html
Copyright © 2011-2022 走看看