洛谷 P1712 [NOI2016]区间(线段树)

传送门

考虑将所有的区间按长度排序

考虑怎么判断点被多少区间覆盖,这个可以离散化之后用一棵权值线段树来搞

然后维护两个指针$l,r$,当被覆盖次数最多的点的覆盖次数小于$m$时不断右移$r$,在覆盖次数大于等于$m$时不断右移$l$,然后每一次用$len[r]-len[l]$更新答案,其中$len$表示该区间的长度

 //minamoto
#include<iostream>
#include<cstdio>
#include<algorithm>
#define inf 0x3f3f3f3f
using namespace std;
#define getc() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++)
char buf[<<],*p1=buf,*p2=buf;
template<class T>inline bool cmax(T&a,const T&b){return a<b?a=b,:;}
template<class T>inline bool cmin(T&a,const T&b){return a>b?a=b,:;}
inline int read(){
#define num ch-'0'
char ch;bool flag=;int res;
while(!isdigit(ch=getc()))
(ch=='-')&&(flag=true);
for(res=num;isdigit(ch=getc());res=res*+num);
(flag)&&(res=-res);
#undef num
return res;
}
const int N=5e5+;
int sum[N<<],add[N<<],L[N],R[N],val[N<<],n,m,lim,cnt,ans=inf;
struct node{
int len,id;
node(){}
node(int len,int id):len(len),id(id){}
inline bool operator <(const node &b)const
{return len<b.len;}
}a[N];
inline void upd(int p){
if(add[p]){
add[p<<]+=add[p],add[p<<|]+=add[p];
sum[p<<]+=add[p],sum[p<<|]+=add[p];
add[p]=;
}
}
void update(int p,int l,int r,int ql,int qr,int val){
if(ql>r||qr<l) return;
if(ql<=l&&qr>=r) return (void)(add[p]+=val,sum[p]+=val);
int mid=(l+r)>>;upd(p);
update(p<<,l,mid,ql,qr,val);
update(p<<|,mid+,r,ql,qr,val);
sum[p]=max(sum[p<<],sum[p<<|]);
}
int main(){
// freopen("testdata.in","r",stdin);
n=read(),m=read();
for(int i=;i<=n;++i)
L[i]=val[++cnt]=read(),R[i]=val[++cnt]=read(),a[i]=node(R[i]-L[i],i);
sort(a+,a++n);
sort(val+,val++cnt),lim=unique(val+,val++cnt)-val-;
for(int i=;i<=n;++i)
L[i]=lower_bound(val+,val++lim,L[i])-val,R[i]=lower_bound(val+,val++lim,R[i])-val;
int l=,r=;
while(true){
while(sum[]<m&&r<n){
int i=a[++r].id,u=L[i],v=R[i];
update(,,lim,u,v,);
}
if(sum[]<m) break;
while(sum[]>=m&&l<n){
int i=a[++l].id,u=L[i],v=R[i];
update(,,lim,u,v,-);
}
cmin(ans,a[r].len-a[l].len);
}
printf("%d\n",ans==inf?-:ans);
return ;
}
上一篇:vs2010编译错误(报错:LINK : fatal error LNK1123: 转换到 COFF 期间失败: 文件无效或损坏)


下一篇:【洛谷 P1712】 [NOI2016]区间 (线段树+尺取)