有N个机器与M个任务,每个机器或者任务都有两个属性(x,y)。
机器的x表示这个机器的最长工作时间, y表示机器的等级。
任务的x表示完成这个任务需要花费的时间,y表示任务的等级。
每个机器只能做一个任务,机器的等级必须大于等于任务的等级。
每完成一个任务可以获得500 * x + 2 * y500∗x+2∗y的价值(x,y是任务的x,y)。
请问最多可以完成多少个任务以及在此基础上最多可以获得多少的价值。
输入
第一行两个整数N(1 \le N \le 100000)N(1≤N≤ 100000)和M(1 \le M \le 100000)M(1≤M≤ 100000)。
接下来N行给出每个机器的x,y。
再接下来M行给出每个任务的x,y。
( 0 < x <1440, 0<=y <= 100) ( 0<x<1440,0<=y<=100) 。
输出
输出两个整数,表示最多可以完成多少个任务,以及在此基础上最多可以获得的价值。
样例
输入
复制
1 2 100 3 100 2 100 1
输出
复制
1 50004
提示
子任务1,20分,1 \le N \le 91≤N≤ 9,1 \le M \le 91≤M≤ 9。
子任务2,30分,1 \le N \le 1001≤N≤ 100,1 \le M \le 1001≤M≤ 100。
子任务3,50分,1 \le N \le 10^51≤N≤ 105,1 \le M \le 10^51≤M≤ 105。
贪心思想,不是拿机器去找任务,而是拿任务去找机器,原本拿机器找任务怎么排序都不对。
时间权重大一些(等级最高100,所以等级不会影响到时间的权重),所以排序的时候以时间为主,等级为辅。每次拿出价值最高的任务去找机器,记录可以用的机器有多少个,对应到等级,这样记录的机器后面的任务都可以用,只是看等级合不合适就可以的。
#include <iostream> #include <cstdio> #include <cmath> #include <vector> #include <algorithm> #include <set> using namespace std; using pa = std::pair<int, int>; int main() { int n, m; int x, y; scanf("%d%d", &n, &m); std::vector<pa> machine(n), task(m); std::vector<int> level(101, 0); for (int i = 0; i < n; i++) { scanf("%d%d", &x, &y); machine[i] = std::make_pair(x, y); } for (int i = 0; i < m; i++) { scanf("%d%d", &x, &y); task[i] = std::make_pair(x, y); } auto cmp = [](const pa& a, const pa& b)->bool { if (a.first == b.first) { return a.second > b.second; } return a.first > b.first; }; sort(machine.begin(), machine.end(), cmp); sort(task.begin(), task.end(), cmp); long long ans = 0; int num = 0; for (int i = 0,j = 0; i < m; i++) { while (j < n && machine[j].first >= task[i].first) { level[machine[j].second]++; j++; } for (int k = task[i].second; k <= 100; k++) { if (level[k]) { level[k]--; num++; ans += 500 * task[i].first + 2 * task[i].second; break; } } } printf("%d %lld", num, ans); return 0; }
如果觉得有帮助,点个推荐啦~