做法为神秘的二分,WA on #3,#8
#include<bits/stdc++.h>
using namespace std;
struct node
{
int p,time;
}q[1000001];
int ans[3];
int a[1000001],b[1000001];//a为最大值,b为最小值
int n,d,mxn;
bool cmp(node a,node b)
{
return a.p<b.p;
}
bool check(int m)
{
memset(a,-1,sizeof(a));
memset(b,100,sizeof(b));
deque<int>q1;
deque<int>q2;
for(int i=1;i<=n;i++)
{
a[q[i].p]=max(a[q[i].p],q[i].time);
b[q[i].p]=min(b[q[i].p],q[i].time);
}//把值赋到a,b两个数组里然后滑动窗口
for(int i=0;i<=mxn+m;i++)
{
if(a[i]!=-1)//没有值的地方不入队
{
while(!q1.empty()&&a[i]>=a[q1.back()])
q1.pop_back();
while(!q2.empty()&&b[i]<=b[q2.back()])
q2.pop_back();
q1.push_back(i);
q2.push_back(i);
}
while(!q1.empty()&&q1.front()<i-m+1)
q1.pop_front();
while(!q2.empty()&&q2.front()<i-m+1)
q2.pop_front();//清除长度超过m的部分
if(!q1.empty()&&!q2.empty())
{
ans[1]=a[q1.front()];
ans[2]=b[q2.front()];
if(ans[1]-ans[2]>d)
return true;//记录答案,判断
}
}
return false;
}
int main()
{
cin>>n>>d;
for(int i=1;i<=n;i++)
{
cin>>q[i].p>>q[i].time;
mxn=max(mxn,q[i].p);//记录最大值,但是好像直接用q[n].p也可以
}
sort(q+1,q+n+1,cmp);//排序
int l=1,r=1000100,tot=1e9;//二分
while(l<=r)
{
int mid=(l+r)/2;
if(!check(mid))
l=mid+1;
else
r=mid-1,tot=min(tot,mid);
}
cout<<(tot>1000000?-1:tot-1);//判有解,但是好像这里炸了,没看出来为什么
}