首页 > 代码库 > 【HDOJ】5155 Harry And Magic Box

【HDOJ】5155 Harry And Magic Box

DP。dp[i][j]可以表示i行j列满足要求的组合个数,考虑dp[i-1][k]满足条件,那么第i行的那k列可以为任意排列(2^k),其余的j-k列必须全为1,因此dp[i][j] += dp[i-1][k]*(2^k)*C(j, k)。

 1 /* 5155 */ 2 #include <cstdio> 3 #include <cstring> 4 #include <cstdlib> 5  6 #define MAXN 51 7  8 const __int64 MOD = 1e9+7; 9 __int64 dp[MAXN][MAXN];10 __int64 C[MAXN][MAXN];11 __int64 two[MAXN];12 13 void init() {14     int i, j, k, tmp;15     16     two[0] = 1;17     for (i=1; i<MAXN; ++i) {18         two[i] = (two[i-1] << 1);19         two[i] %= MOD;20     }21     22     C[1][0] = C[1][1] = 1;23     for (i=2; i<MAXN; ++i) {24         C[i][0] = C[i][i] = 1;25         for (j=1; j<i; ++j) {26             C[i][j] = C[i-1][j] + C[i-1][j-1];27             C[i][j] %= MOD;28         }29     }30     31     for (i=0; i<MAXN; ++i)32         dp[i][1] = dp[1][i] = 1;33     34     for (i=2; i<MAXN; ++i) {35         for (j=1; j<MAXN; ++j) {36             dp[i][j] = dp[i-1][j]*(two[j]-1)%MOD;37             for (k=1; k<j; ++k) {38                 dp[i][j] += dp[i-1][k]*C[j][k]%MOD*two[k];39                 dp[i][j] %= MOD;40             }41         }42     }43 }44 45 int main() {46     int n, m;47     48     #ifndef ONLINE_JUDGE49         freopen("data.in", "r", stdin);50         freopen("data.out", "w", stdout);51     #endif52     53     init();54     while (scanf("%d %d", &n, &m) != EOF)55         printf("%I64d\n", dp[n][m]);56     57     return 0;58 }

 

【HDOJ】5155 Harry And Magic Box