hdu 4869 Task(馋)

题目链接:hdu 4869 Task

题目大意:有n台机器,m个任务。每一个机器和任务都有有xi和yi。要求机器的xi。yi均大于等于任务的xi和yi才干运行任务。

每台机器一天仅仅能运行一个任务。要求完毕的任务数尽量多,而且说金额尽量大。

完毕每一个任务的金额为xi500+yi2

解题思路:贪心,mach[i][j]表示等级为i,时间为j的机器数量,task[i][j]表示等级为i,时间为j的机器数量。

每次优先降低i,由于相应等级降低100,相应的金额代价也不会降低超过500(即时间降低1)。
每次mach[i][j]要加上mach[i][j+1],即上面没有被使用的机器。tmp记录当前j下,等级大于i的机器个数。

#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>

using namespace std;
typedef __int64 ll;
const int maxt = 1440;
const int maxd = 100;

int N, M;
int mach[maxd+10][maxt+10], task[maxd+10][maxt+10];

void init () {
    int a, b;
    memset(mach, 0, sizeof(mach));
    memset(task, 0, sizeof(task));

    for (int i = 0; i < N; i++) {
        scanf("%d%d", &a, &b);
        mach[b][a]++;
    }

    /*
    for (int i = maxd; i >= 0; i--)
        for (int j = maxt; j >= 0; j--)
            mach[i][j] = mach[i][j] + mach[i+1][j] + mach[i][j+1] - mach[i+1][j+1];
            */

    for (int i = 0; i < M; i++) {
        scanf("%d%d", &a, &b);
        task[b][a]++;
    }
}

void solve () {
    ll ans = 0;
    int cnt = 0;

    for (int j = maxt; j >= 0; j--) {
        int tmp = 0;
        for (int i = maxd; i >= 0; i--) {

            mach[i][j] += mach[i][j+1];
            tmp += mach[i][j];

            int k = min(tmp, task[i][j]);
            ans += (ll)k * (2LL * i + 500LL * j);
            tmp -= k;
            cnt += k;

            for (int x = i; x <= maxd; x++) {
                int p = min(mach[x][j], k);
                k -= p;
                mach[x][j] -= p;

                if (k == 0)
                    break;
            }
        }
    }
    printf("%d %I64d
", cnt, ans);
}

int main () {
    while (scanf("%d%d", &N, &M) == 2 && N + M) {
        init();
        solve();
    }
    return 0;
}

版权声明:本文博主原创文章,博客,未经同意不得转载。

原文地址:https://www.cnblogs.com/mengfanrong/p/4791678.html