# How many trees?

$f_{i,j}$表示$i$个节点，最大深度为$j$的方案，$g_{i,j}=\sum\limits_{k = 1}^{j - 1} f_{i, k}$。

#include <bits/stdc++.h>

#define setIO(s) freopen(s".in", "r", stdin), freopen(s".out", "w", stdout)

#define N 2010

using namespace std;

typedef long long ll;

const int mod = 998244353 ;

int qpow(int x, int y) {
int ans = 1;
while (y) {
if (y & 1) {
ans = (ll)ans * x % mod;
}
y >>= 1;
x = (ll)x * x % mod;
}
return ans;
}

int f[N][N], g[N][N], a[N], b[N];

int main() {
// setIO("count");
int n, h;
cin >> n >> h ;
f[1][1] = 1;
g[0][0] = 1;
for (int dep = 1; dep <= n; dep ++ ) {
g[dep][0] = 1;
}
for (int dep = 2; dep <= n; dep ++ ) {
g[dep][1] = 1;
}
for (int dep = 2; dep <= n; dep ++ ) {
// for (int i = 1; i <= n; i ++ ) {
//     a[i] = f[dep - 1][i], b[i] = g[dep - 1][i];
// }
// a * a + 2 * a * b
for (int l = 0; l <= n; l ++ ) {
for (int r = 0; r <= n; r ++ ) {
if (l + r + 1 <= n) {
(f[dep][l + r + 1] += (ll)f[dep - 1][l] * f[dep - 1][r] % mod) %= mod;
(f[dep][l + r + 1] += (ll)f[dep - 1][l] * g[dep - 1][r] % mod * 2 % mod) %= mod;
}
}
}
for (int i = 1; i <= n; i ++ ) {
g[dep][i] = (g[dep - 1][i] + f[dep - 1][i]) % mod;
}
// printf("Dep : %d\n", dep);
// for (int j = 1; j <= n; j ++ ) {
//     printf("%d ", f[dep][j]);
// }
// puts("");
}
int ans = 0;
for (int i = h; i <= n; i ++ ) {
(ans +=
f[i][n]) %= mod;
}
cout << ans << endl ;
return 0;
}
posted @ 2019-10-31 18:22  JZYshuraK_彧  阅读(237)  评论(0编辑  收藏  举报