[USACO15OPEN] Trapped in the Haybales S题解
题目描述
FJ 收到了 N 捆干草,并将它们放置在连接房屋与谷仓的道路上。第 j 捆干草的大小为 Sj,位置为 Pj。Bessie 一开始在 B 处,不与任何一捆干草的位置重合。
Bessie 可以在干草捆之间任意移动(也可以到达干草捆所在的位置),但不能越过干草捆。但凡事总有例外:当 Bessie 进行了长度为 D 的冲刺后,她就可以击碎一捆大小严格小于 D 的干草,这意味着这捆干草不复存在。
由于某些原因,FJ 希望把 Bessie 困在最左边与最右边的干草捆之间。为此,他希望将某一捆干草的大小增加一些。如果可能把 Bessie 困住,请输出他最少需要增加多少干草;否则输出 -1。
1⩽N⩽105,1⩽Si,Pi,B⩽109。
输入格式
第一行,两个整数 N,B,分别表示干草捆数量与 Bessie 所在位置。
接下来 N 行,第 i 行为两个整数 Si,Pi,分别表示第 i 捆干草的大小与位置。
输出格式
如果可能把 Bessie 困住,输出一行一个整数,表示最少需要增加多少干草;否则输出 -1。
Translated by KHIN.
显示翻译
题意翻译
输入输出样例
输入 #1复制
5 7 8 1 1 4 3 8 12 15 20 20
输出 #1复制
4
思路
贪心+DP。
代码见下
#include<bits/stdc++.h>
using namespace std;
long long n,b,db=0,l,r,lk=1e18+7;
struct one{
long long s,p;
}a[100005];
bool cmp(one a1,one b1){
return a1.p<b1.p;
}
int main(){
cin>>n>>b;
for(int i=1;i<=n;i++){
cin>>a[i].s>>a[i].p;
}
sort(a+1,a+n+1,cmp);
if(a[1].p>=b||a[n].p<=b){
cout<<-1<<endl;
}
else{
for(int i=2;i<=n;i++){
if(a[i].p>=b){
db=i-1;
break;
}
}
r=db+1;
for(int i=db;i>=1;i--) {
while(r<=n&&a[r].p-a[i].p>a[r].s){
r++;
}
if(r>=n+1){
break;
}
lk=min(lk,a[r].p-a[i].p-a[i].s);
}
l=db;
for(int i=db+1;i<=n;i++){
while(l>=1&&a[i].p-a[l].p>a[l].s){
l--;
}
if(l<=0){
break;
}
lk=min(lk,a[i].p-a[l].p-a[i].s);
}
if(lk>=1e15){
cout<<-1<<endl;
}
else{
cout<<max(lk,0ll)<<endl;
}
}
return 0;
}

浙公网安备 33010602011771号