func_code_string: #include <bits/stdc++.h>   using namespace std;   const int MOD = 1e9 + 7;   void add(int& x, int y) { ((x += y) >= MOD) && (x -= MOD); }   void sub(int& x, int y) { add(x, -y + MOD); }   int mul(int x, int y) { return x * 1ll * y % MOD; }   int mpow(int a, int p) {     int res = 1;     for (; p > 0; p >>= 1, a = mul(a, a)) {       if (p & 1) {         res = mul(res, a);       }     }     return res;   }   const int MAXN = 50 + 10;   int mem_inv[MAXN];   int inv(int x) {     int& y = mem_inv[x];     if (y) {       return y;     }     y = mpow(x, MOD - 2);     assert(mul(x, y) == 1);     return y;   }   int n, m;   bool read() {     if (scanf( %d%d , &n, &m) < 2) {       return 0;     }     n += 2;     return 1;   }   int dp2[MAXN][MAXN];   int dp[MAXN][MAXN];   int dp_big[MAXN][MAXN][MAXN][MAXN];   int binom(int n, int k) {     assert(k);     add(n, k - 1);     int ans = 1;     for (int i = 0; i < int(k); ++i) {       int cur_n = n;       sub(cur_n, i);       ans = mul(ans, cur_n);       ans = mul(ans, inv(i + 1));     }     return ans;   }   int calc_dp(int, int);   int calc_dp2(int, int);   int calc_dp_big(int, int, int, int);   int calc_dp2(int n, int m) {     if (n < 3) {       return 0;     }     int& mem = dp2[n][m];     if (mem != -1) {       return mem;     }     int ans = 0;     for (int n_left = 2; n_left < n; ++n_left) {       const int n_right = n - n_left + 1;       for (int m_right = m; m_right < MAXN; ++m_right) {         add(ans, mul(calc_dp(n_left, m), calc_dp(n_right, m_right)));       }       for (int m_left = m + 1; m_left < MAXN; ++m_left) {         add(ans, mul(calc_dp(n_left, m_left), calc_dp(n_right, m)));       }     }     return (mem = ans);   }   int calc_dp_big(int n, int m, int n1, int m1) {     if (n < 2) {       return 0;     }     if (n == 2) {       return (m == 0);     }     if (m <= 0 || n1 < 3) {       return 0;     }     assert(m1 >= 0);     int& mem = dp_big[n][m][n1][m1];     if (mem != -1) {       return mem;     }     int new_n1 = n1;     int new_m1 = m1 - 1;     if (new_m1 == -1) {       new_n1--;       new_m1 = MAXN - 1;     }     int ans = 0;     for (int cnt = 0; (n1 - 2) * cnt + 2 <= n && m1 * cnt <= m; ++cnt) {       int cur = cnt ? binom(calc_dp2(n1, m1), cnt) : 1;       int will = calc_dp_big(n - (n1 - 2) * cnt, m - m1 * cnt, new_n1, new_m1);       add(ans, mul(cur, will));     }     return (mem = ans);   }   int calc_dp(int n, int m) {     int& mem = dp[n][m];     if (mem != -1) {       return mem;     }     int ans = calc_dp_big(n, m - 1, MAXN - 1, MAXN - 1);     return (mem = ans);   }   int solve() {     memset(dp2, -1, sizeof dp2);     memset(dp, -1, sizeof dp);     memset(dp_big, -1, sizeof dp_big);     return calc_dp(n, m);   }   int main() {     while (read()) {       printf( %d n , solve());     }     return 0;   }   