zoukankan      html  css  js  c++  java
  • lightoj 1226

    题目链接:http://www.lightoj.com/volume_showproblem.php?problem=1226

    题解:由于这些任务完成是有先后的所以最后一个完成的肯定是最后一个任务的子任务,不妨设dp[i]表示第几个任务完成后总共有几种方案,这里要逆着来至于为什么想想也是挺好理解的。于是有这么一个方程式dp[i]=dp[i + 1]*C(sum-1,k[i]-1),这样列出来就更好理解了。就是最后一个位置肯定是确定的之后就靠组合来凑。

    #include <iostream>
    #include <cstring>
    #include <cstdio>
    #define mod 1000000007
    using namespace std;
    typedef long long ll;
    const int M = 1234;
    ll k[M];
    ll dp[M] , Po[1234567];
    ll mod_pow(ll a , ll b) {
        ll res = 1;
        while(b) {
            if(b & 1) res = (res * a) % mod;
            a = (a * a) % mod;
            b >>= 1;
        }
        return res;
    }
    ll C(ll n , ll m) {
        if(n < m) return 0;
        if(!m || !n) return 1;
        ll res = (Po[n] * mod_pow(Po[m] * Po[n - m] % mod , mod - 2)) % mod;
        return res;
    }
    int main() {
        int t , n;
        scanf("%d" , &t);
        int Case = 0;
        Po[0] = 1;
        for(int i = 1 ; i < 1234567 ; i++) {
            Po[i] = Po[i - 1] * i % mod;
            Po[i] %= mod;
        }
        while(t--) {
            memset(dp , 0 , sizeof(dp));
            scanf("%d" , &n);
            ll sum = 0;
            for(int i = 1 ; i <= n ; i++) {
                scanf("%lld" , &k[i]);
                sum += k[i];
            }
            dp[n] = C(sum - 1 , k[n] - 1);
            dp[n] %= mod;
            sum -= k[n];
            for(int i = n - 1 ; i >= 1 ; i--) {
                dp[i] = dp[i + 1] * C(sum - 1 , k[i] - 1) % mod;
                dp[i] %= mod;
                sum -= k[i];
            }
            printf("Case %d: %lld
    " , ++Case , dp[1]);
        }
        return 0;
    }
  • 相关阅读:
    OSG开源教程(转)
    小组项目工作分配,任务确认
    OSG安装编译
    JAVA开发工具IDEA使用体验
    软件工程结对项目总结
    迭代开发个人总结20160705
    迭代开发个人总结20160704
    迭代开发个人总结20160703
    迭代开发个人总结20160702
    迭代开发个人总结20160701
  • 原文地址:https://www.cnblogs.com/TnT2333333/p/7656581.html
Copyright © 2011-2022 走看看