常州买衣服(优先队列)
常州买衣服
时间限制: 1 Sec 内存限制: 128 MB
题目描述
不知道是拔河训练的作用还是那个梦的缘故,反正小X是一天天瘦下来了,虽然还没有中天学长那么帅,但比起 Q 老师已经瘦了很多,小X原先买的衣服都嫌大了,于是他想去买些新衣服,小X的衣服原先一直是在非主流服装店买的,他的衣服一般店里是买不到的,而去非主流服装店肯定能买到,如膝盖上挖了两个洞的牛仔裤,正常人穿了像雨衣的冲锋衣等应有尽有,并且每买一件就送一张优惠券,小X这些年下来积聚了好多张优惠券,这次非主流服装店恰好举行优惠活动,用优惠券购买衣服可享受优惠价!
小X来到了非主流服装店,他看上了 n 件衣服,每一件衣服价格为 Pi,小X现在手***有 m 个单位的现金,以及 k 张优惠卷。小X可以在购买某件衣服时,使用至多一张优惠券,若使用优惠券,则该衣服的价格会下降至 Qi,小X想知道他最多可以买几件衣服。
输入
第一行包含三个用空格隔开的正整数 n,k,m,依次表示衣服总数和优惠券数量及现金总数。
接下来 n 行每行包含两个整数 Pi,Qi,表示该件衣服的价格和优惠价。数据保证 Pi>=Qi。
输出
输出数据仅有一行包含一个整数,表示小 X 最多能购买的衣服数。
样例输入
复制样例数据
4 1 7 3 2 2 2 8 1 4 3
样例输出
3
提示
30%的数据,n<=5,k=1,m<=100
对于另外 10%的数据,n<=5,k<=5,m<=100
60%的数据,n<=200,k<=200
80%的数据,n<=2500,k<=2500
100%的数据,n<=50000,k<=50000,m<=10^16
用优先队列做,首先将所有的衣服放进队列中,然后再把打折后的衣服放进去一次,然后优先队列出队;
维护两点: 1.是否还有打折券
2.是否钱还够
3.选了打折的衣服就不能再选同一件没打折的衣服。
/**/
#include <cstdio>
#include <cstring>
#include <cmath>
#include <cctype>
#include <iostream>
#include <algorithm>
#include <map>
#include <set>
#include <vector>
#include <string>
#include <stack>
#include <queue>
typedef long long LL;
using namespace std;
int n, k, vis[50005];
LL m;
struct node
{
LL p, w;
int id;
bool operator <(const node &x)const{
return p > x.p;
}
}a[50005];
priority_queue<node> q;
int main()
{
//freopen("in.txt", "r", stdin);
//freopen("out.txt", "w", stdout);
scanf("%d %d %lld", &n, &k, &m);
for (int i = 1; i <= n; i++){
scanf("%lld %lld", &a[i].p, &a[i].w);
a[i].id = i;
q.push(a[i]);
}
node t;
for (int i = 1; i <= n; i++){
t.p = a[i].w, t.w = -1, t.id = a[i].id;
q.push(t);
}
LL sum = 0;
int ans = 0;
while(q.size()){
node t = q.top();
q.pop();
if(vis[t.id] || (t.w == -1 && !k)) continue;
if(sum + t.p > m) break;
ans++, sum += t.p;
vis[t.id] = 1;
if(t.w == -1) k--;
}
printf("%d\n", ans);
return 0;
}
/**/