• HDU-4248 A Famous Stone Collector 组合数学 DP


    HDU 4248

    题意:

    给定n种颜色不同的石子,每种石头有 num[i] 个。从中取石子,问能够得到多少种不同的序列。

    [n leq 100,num[i]leq 100 ]

    数据范围比较小,考虑dp

    [dp[i][j]表示选前i种石头,且选的石头总数为j时的不同序列个数 ]

    有转移方程

    [dp[i][j] = sum dp[i - 1][j - k] cdot binom{j}{k} quad kleq num[i] ]

    即考虑第i种石头的贡献,也就是第j个中选k个位置给第i种石头。

    [ans = sum dp[n][i]quad i leq sum ]

    ll C[10015][105];
    
    void init() {
        for (int i = 0; i < 10015; i++) {
            C[i][0] = 1;
            for (int j = 1; j <= i && j <= 105; j++)
                C[i][j] = (C[i - 1][j - 1] + C[i - 1][j]) % MOD;
        }
    }
    
    int num[105];
    ll dp[105][10005];
    
    int main() {
        int n;
        init();
        int kase = 1;
        while (~scanf("%d", &n)) {
            ll sum = 0;
            for (int i = 1; i <= n; i++) num[i] = readint();
            memset(dp, 0, sizeof dp);
            dp[0][0] = 1;
            for (int i = 1; i <= n; i++) {
                sum += num[i];
                for (int j = 0; j <= sum; j++) {
                    for (int k = 0; k <= num[i] && j >= k; k++)
                        dp[i][j] += dp[i - 1][j - k] * C[j][k], dp[i][j] %= MOD;
                }
            }
            ll res = 0;
            for (int i = 1; i <= sum; i++) res += dp[n][i], res %= MOD;
            printf("Case %d: ", kase++);
            Put(res);
            puts("");
        }
    }
    
  • 相关阅读:
    《人件》阅读笔记五
    《人件》阅读笔记四
    《人件》阅读笔记三
    《人件》阅读笔记二
    《人件》阅读笔记一
    年报系统课堂讨论记录
    系统利益相关者描述案例
    Android开发学习记录--活动生命周期
    jQuery AJAX简介
    jQuery HTML简介
  • 原文地址:https://www.cnblogs.com/hznumqf/p/13534497.html
Copyright © 2020-2023  润新知