7_4_F题 Task 题解[hdu 4846](贪心)

来源:互联网 发布:网络博物馆 编辑:程序博客网 时间:2024/06/05 09:24

题目链接

简单题意

有若干机器和任务,每个机器都有一个工作时间t1和等级v1
任务也有对应的t2和等级v2,一个任务能被机器执行的条件是 t1t2 & v1v2,任务被执行之后获得 500t2+2v2 的报酬,一台机器一天最多执行一次任务。求最多能执行多少任务,获得的收益最大是多少。

思路

因为很明显时间的权重要远大于等级,所以优先考虑时间长的任务能被执行。贪心,先把任务和机器都按先时间后等级的优先级降序排列,然后遍历所有的任务,对每个任务,选择能满足他时间要求的机器中,等级最小但大于他的那个。代码写的比较清楚

代码

#include <cstdio>#include <algorithm>#include <set>using namespace std;typedef long long ll;const int maxn = 1e5+10;struct STD{    int lv,ti;    friend bool operator < (STD a,STD b){        if(a.lv == b.lv)            return a.ti < b.ti;        return a.lv < b.lv;    }};STD machine[maxn];STD task[maxn];bool cmp(STD &a, STD &b){    if(a.ti == b.ti)        return a.lv > b.lv;    return a.ti > b.ti;}bool cheak(STD &a, STD &b){    if(a.ti <= b.ti) return true;    return false;}int main (){    int n,m;    multiset<STD> ms;    while(~scanf("%d %d",&n,&m)){        ll ans = 0;        for(int i = 0 ; i < n ; i ++){            scanf("%d %d",&machine[i].ti,&machine[i].lv);        }        for(int i = 0 ; i < m ; i ++){            scanf("%d %d",&task[i].ti,&task[i].lv);        }        sort (machine,machine + n,cmp);        sort (task,task + m,cmp);        int cnt = 0;        for(int i = 0, k = 0 ; i < m ; i ++){            while(k < n && cheak(task[i],machine[k])){                ms.insert(machine[k]);                k ++;            }            auto it = ms.lower_bound(task[i]);            if(it != ms.end()){                ans += task[i].ti*500+2*task[i].lv;                cnt ++;                ms.erase(it);            }        }        printf("%d %I64d\n",cnt,ans);        ms.clear();    }}
0 0
原创粉丝点击