题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4268
题意:A,B各有n张牌,A要用自己的牌覆盖B的牌,求A最多能覆盖多少张。
牌有长h和宽w两个属性,当一张牌能覆盖另一张牌,它的长宽都必须不小于另一张牌。
思路:将A,B的牌都按h(或者w)由小到大排序,然后把B的所有不大于A[0]的 h 的牌都放入multiset中(注意,扔掉h这一维,只放w即可),再在multiset中二分查找最后一张不大于A[0A]的 w 的牌,找到一张最优的可覆盖的牌,将此牌删去,答案加1,之后以此类推。
#include <cstdio> #include <cmath> #include <iostream> #include <algorithm> #include <string> #include <cstring> #include <stdlib.h> #include <stack> #include <queue> #include <iterator> #include <set> #include <ctype.h> using namespace std; const int maxn = 100000 + 50; multiset <int> ms; multiset <int> :: iterator it; struct card { int h; int w; } a[maxn], b[maxn]; int cmp(card a, card b) { return a.h <= b.h; } int main() { int t; scanf("%d", &t); while(t--) { int n; int sum = 0; scanf("%d", &n); for(int i = 0; i < n; i++) scanf("%d%d", &a[i].h, &a[i].w); for(int i = 0; i < n; i++) scanf("%d%d", &b[i].h, &b[i].w); sort(a, a + n, cmp); sort(b, b + n, cmp); ms.clear(); int i, j = 0; for(i = 0; i < n; i++) { while(j < n && b[j].h <= a[i].h) { ms.insert(b[j].w); j++; } if(!ms.empty()) { it = ms.upper_bound(a[i].w); if (it != ms.begin()) { ms.erase(--it); sum++; } } } printf("%d\n", sum); } }
HDU 4268 Alice and Bob (set+贪心)
最新推荐文章于 2021-09-01 19:57:26 发布