【2019年CCPC网络赛】【HDU 6709】【Fishing Master】【贪心】

题目链接:
http://acm.hdu.edu.cn/showproblem.php?pid=6709
题意:
n n n条鱼,抓每条鱼需要 k k k分钟,煮每条鱼至少需要 t i t_i ti分钟,可以在煮鱼的时候去抓鱼,但不能在抓鱼的时候去捕鱼,问最少花费时间。
题解:
这里不确定的就是,在煮鱼的过程中,到底是先去抓鱼还是再等等。
所以不如先把一定能确定的考虑掉,即当 k ≤ t i k\leq t_i kti的时候,我们肯定是先抓 t i k \frac{t_i}{k} kti条鱼,至于剩下的 t i % k t_i\%k ti%k,不如等等考虑。
所以说,我们一定能抓的鱼的数量就能确定了, c n t = 1 + ∑ t i k cnt=1+\sum \frac{t_i}{k} cnt=1+kti(这里+1是因为最开始第一条鱼一定要抓)
现在来考虑是等还是先去抓了在来把煮的鱼捞起来
现在每个 t i t_i ti不确定的时间为 t i % k t_i\%k ti%k,不妨记做 T i T_i Ti,现在只有两种情况:

直接等,那么花费时间为 T i T_i Ti
先去抓鱼在来,那么你空闲的没有煮鱼的时间就是 k − T i k-T_i kTi,也就是没有充分利用的时间,被你浪费

那么现在已经抓的鱼有 c n t cnt cnt条,剩下 s u m = n − c n t sum=n-cnt sum=ncnt条没有抓,为了耗时最少,我们肯定是要让浪费的时间最少,也就是选取 s u m sum sum条浪费时间最少(即 T i T_i Ti最大的sum条),其余的煮鱼都是等待(加上等待时间),这样就是答案了。
代码:

#include<bits/stdc++.h>
#define INF 0x3f3f3f3f
#define sz sizeof
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef pair<int, int> Pair;
const int MAX = 1e5 + 10;

ll n, k;
ll t[MAX];

int main() {
     
#ifdef ACM_LOCAL
    freopen("input.txt", "r", stdin);
    freopen("output.txt", "w", stdout);
#endif
    int T;
    scanf("%d", &T);
    while (T--) {
     
        scanf("%lld%lld", &n, &k);
        ll sum = n - 1, cnt = 1;
        for (int i = 1; i <= n; i++) {
     
            scanf("%lld", &t[i]);
            sum -= t[i] / k;
            cnt += t[i] / k;
            t[i] %= k;
        }
        sort(t + 1, t + 1 + n);
        ll ans = cnt * k;
        for (int i = n; i >= 1; i--) {
     
            if (sum > 0)ans += k, sum--;
            else ans += t[i];
        }
        printf("%lld\n", ans);
    }
    return 0;
}

你可能感兴趣的:(#,贪心,思维,ACM)