版权声明:最后一年,加油~ https://blog.csdn.net/zzti_xiaowei/article/details/81913062
思路:
一开始就想到用二分答案,写着写着一直T,没有对堆进行预处理。改之,由于一个小bug,一直WA。然后AC之后,讨论区看一下,此题数据较弱,好多二分中位数位置k,用堆找出前n/2和后n/2的最小和与总金额f进行比较,从而l++或者r–的做法是错误的,这样不满足单调性,无法二分!
- 数据:
3 5 3
4 10
5 10
6 1
7 1
8 1
正确做法:直接从后向前枚举中位数,符合即为最优!
代码:
//二分枚举中位数(其实是不对的)
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<algorithm>
using namespace std;
const int Max_n=1e5+10;
int n,c,f;
struct cow{
int a,b;
bool operator<(const cow &c)const {
return a<c.a;
}
}co[Max_n];
int p[Max_n],q[Max_n]; //堆的预处理
bool jud(int k){
if(p[k-1]+q[k+1]+co[k].b<=f)return true;
return false;
}
int main()
{
scanf("%d%d%d",&n,&c,&f);
for(int i=0;i<c;i++)scanf("%d%d",&co[i].a,&co[i].b);
sort(co,co+c);
int t=n/2,sum=0;
if(n==1){ //n==1特判 (不加竟然AC)
int i=c-1;
for(;i>=0;i--){
if(co[i].b<=f){
printf("%d\n",co[i].a);
break;
}
}
if(i<0)printf("-1\n");
return 0;
}
priority_queue<int>que;
sum=0;
for(int i=0;i<c;i++){
que.push(co[i].b);
sum+=co[i].b;
if(i==t-1)p[i]=sum;
if(i>t-1){
sum-=que.top();
p[i]=sum;
que.pop();
}
}
sum=0;
for(int i=c-1;i>=0;i--){
que.push(co[i].b);
sum+=co[i].b;
if(i==c-t)q[i]=sum;
if(i<c-t){
sum-=que.top();
q[i]=sum;
que.pop();
}
}
int l=t,r=c-t-1,mid;
while(l<=r){
mid=(l+r)>>1;
if(jud(mid))l++;
else r--;
}
if(r<t)printf("-1\n");
else printf("%d\n",co[r].a);
return 0;
}
// 直接枚举中位数
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<algorithm>
using namespace std;
const int Max_n=1e5+10;
int n,c,f;
struct cow{
int a,b;
bool operator<(const cow &c)const {
return a<c.a;
}
}co[Max_n];
int p[Max_n],q[Max_n]; //堆的预处理
bool jud(int k){
if(p[k-1]+q[k+1]+co[k].b<=f)return true;
return false;
}
int main()
{
scanf("%d%d%d",&n,&c,&f);
for(int i=0;i<c;i++)scanf("%d%d",&co[i].a,&co[i].b);
sort(co,co+c);
int t=n/2,sum=0;
if(n==1){ //n==1特判 (不加竟然AC)
int i=c-1;
for(;i>=0;i--){
if(co[i].b<=f){
printf("%d\n",co[i].a);
break;
}
}
if(i<0)printf("-1\n");
return 0;
}
priority_queue<int>que;
sum=0;
for(int i=0;i<c;i++){
que.push(co[i].b);
sum+=co[i].b;
if(i==t-1)p[i]=sum;
if(i>t-1){
sum-=que.top();
p[i]=sum;
que.pop();
}
}
sum=0;
for(int i=c-1;i>=0;i--){
que.push(co[i].b);
sum+=co[i].b;
if(i==c-t)q[i]=sum;
if(i<c-t){
sum-=que.top();
q[i]=sum;
que.pop();
}
}
int i;
for(i=c-t-1;i>=t;i--){
if(jud(i)){
printf("%d\n",co[i].a);
break;
}
}
if(i<t)printf("-1\n");
return 0;
}