题目描述
现有n组人,m个地点,给出每组人的人数,每个地点可容纳的最大人数和选择的价格
要求一种方式,使得每组人都到一个各不相同的地点,最小化选择的价格
每个队伍的人都要在同一个地方每个地方只能有一个队伍
输入描述:
第一行n,m 第二行n个数,表示每组的人数 接下来m行,每行两个数,表示可容纳的最大人数和选择的价格
输出描述:
输出最小化选择的价格,无解输出-1
示例1
输入
3 4 2 3 4 1 2 2 3 3 4 4 5
输出
12
备注:
所有数据小于1e5
贪心+优先队列,先根据容量排序,然后把能够容纳当前队伍数的房间入队,用优先队列,每次将价格最小的出队,没有则不符合题意。
#include<bits/stdc++.h>
#define ll long long
#include<queue>
using namespace std;
const int maxn = 1e5+7;
int n, m;
ll ans = 0;
ll num[maxn];
bool vis[maxn];
struct node {
ll c, me;
friend bool operator <(node a, node b)
{
return a.me > b.me;
}
}mm[maxn];
bool cmp(node a, node b) {
return a.c >= b.c;
}
int main()
{
//freopen("in.txt", "r", stdin);
while(~scanf("%d%d",&n,&m))
{
memset(vis, 0, sizeof(vis)); ans = 0;
for(int i = 0; i < n; i++) scanf("%lld", &num[i]);
for(int i = 0; i < m; i++) scanf("%lld%lld", &mm[i].c, &mm[i].me);
sort(num, num+n); sort(mm, mm+m, cmp);
priority_queue<node> q;
int j = 0, flag = 1;
for(int i = n - 1; i >= 0; i--)
{
while(j < m&&mm[j].c>= num[i]) {
q.push(mm[j]);
j++;
}
if(q.empty()) flag = 0;
else {
node temp = q.top();
q.pop();
ans += temp.me;
}
}
if(flag == 0) ans = -1;
printf("%lld\n", ans);
}
return 0;
}