Cow Pedigrees

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Cow Pedigrees相关的知识,希望对你有一定的参考价值。

Two possible pedigrees have 5 nodes and height equal to 3:

           @                   @      
          / \                 /          @   @      and      @   @
        / \                     /        @   @                   @   @

题意:给你 n 个元素,可以组成多少颗深度为 m 的二叉树,每个结点的度只有 0 或 2 。


  果然不好下手就是DP题。
本题DP状态定义就显得十分重要了。
如果直接定义dp[i][j] 表示 用i个元素 深度为j的二叉树。发现并不好转移。
于是 别人就想到了 定义dp[i][j]表示 用i个元素按 深度小于等于j的二叉树。?
于是怎么转移呢?

  我们的二叉树可以 分解为 root,lson and rson 。root 占了一个深度。
于是 lson and rson 分别代表的深度只需要小于等于 j-1 再加上root(深度为1) ,总的深度就小于等于j了。
  再于是,DP[i][j] = ∑DP[k][j-1] + DP[i-1-k][j-1](k=1,2.....i-2)
(root用掉一个元素 lson k个 rson i-1-k个)

最后的答案!就是DP[n][k]-DP[n][k-1] 巧妙~
代码:
/*
ID:Andy Chen
PROG:nocows
LANG:C++
*/
#include<cstdio>
#include<iostream>
#include<cstring>
using namespace std;
int dp[300][300];
int n,k;
#define mod 9901
int main()
{
    freopen("nocows.in","r",stdin);
    freopen("nocows.ouw","w",stdout);
    while(scanf("%d%d",&n,&k)!=EOF)
    {
        memset(dp,0,sizeof(dp));
        for(int i=1;i<=k;++i) dp[1][i]=1;
        for(int i=2;i<=n;++i)
            for(int j=1;j<=k;++j)
                for(int p=1;p<=i-2;++p)
                dp[i][j]=(dp[i][j]+dp[p][j-1]*dp[i-1-p][j-1])%mod;
        int ans=(dp[n][k]-dp[n][k-1])%mod;
        if(ans<0) ans+=mod;
        cout<<ans<<endl;
    }
    return 0;

}

 




以上是关于Cow Pedigrees的主要内容,如果未能解决你的问题,请参考以下文章

UASCO Cow Pedigrees /// oj10140

奶牛家谱 Cow Pedigrees

洛谷P1472 奶牛家谱 Cow Pedigrees

luogu1472 奶牛家谱 Cow Pedigrees [动态规划]

usaco-Cow Pedigrees

[luoguP1472] 奶牛家谱 Cow Pedigrees(DP)