2 3 4 0 1 1 0 3 1 1 -1 0 0 1 1 0 -1
2 2
链接:http://acm.hdu.edu.cn/showproblem.php?pid=5091
题意:有n个点,给你w*h的框框,问你最多可以框住几个点,边缘也算。
做法:把每个点x-w/2,y-h/2, 与x+w/2,y+h /2,作一个矩形,可以知道,只有那个框框的中心在这个矩形中就可以覆盖这个点。然后就把所有点的矩形画出来,计算最大重合的层数就行了。实际操作中 可以把每个矩形看作 左下角为 x,y,右上角为x+w,y+h。 也就相当于一起平移。最大重合层数不变。
这题和我之前做得算面积的线段树不同。因为这里关注的不在是面积,所以也就不再关注宽度了。所以这里 线段树里的每个点0-(k-1)代表的不是一段长度的状态了,而是每一个点的状态。
所以本来的 r=Bin(s[i].r,k,x)-1;这一句 由原模版变成了r=Bin(s[i].r,k,x)。
然后就是基本功,把线段树改成算最大值的了。cover记录每个区间最大值。
#include<stdio.h> #include<string.h> #include<algorithm> #include<set> #define ll __int64 using namespace std; #define lson l,m,rt<<1 #define rson m+1,r,rt<<1|1 const ll maxn=50010; struct Seg { ll l,r,h; ll flag; Seg(){} Seg(ll a,ll b,ll c,ll d):l(a),r(b),h(c),flag(d){} bool operator<(const Seg &hh) const { return h<hh.h; } }; struct Seg s[maxn<<3]; ll cover[maxn<<2],add[maxn<<2]; ll x[maxn<<2]; ll ans; void PushUp(ll rt,ll l,ll r) { cover[rt]=max(cover[rt<<1],cover[rt<<1|1])+add[rt]; } void Update(ll L,ll R,ll f,ll l,ll r,ll rt) { if(L<=l && r<=R) { cover[rt]+=f;//这个点的覆盖 add[rt]+=f; return ; } ll m=(l+r)>>1; if(R<=m) Update(L,R,f,lson); else if(L>m) Update(L,R,f,rson); else { Update(L,R,f,lson); Update(L,R,f,rson); } PushUp(rt,l,r); } ll Bin(ll k,ll n,ll x[]) { ll l,r,m; l=0,r=n-1; while(l<=r) { m=(l+r)>>1; if(x[m]==k) return m; else if(x[m]>k) r=m-1; else l=m+1; } return -1; } set<ll> ss; set<ll>::iterator it; int main() { ll n; ll i; ll ww,hh; ll xx,yy; while(scanf("%I64d",&n),n!=-1) { scanf("%I64d%I64d",&ww,&hh); ll m=0; ss.clear(); for(i=0;i<n;i++) { scanf("%I64d %I64d",&xx,&yy); ss.insert(xx+ww); ss.insert(xx); s[m++]=Seg(xx,xx+ww,yy,1); s[m++]=Seg(xx,xx+ww,yy+hh,-1); } sort(s,s+m); ll k=0; for(it=ss.begin();it!=ss.end();it++) x[k++]=*it; memset(cover,0,sizeof cover); memset(add,0,sizeof add); ans=0; for(i=0;i<m-1;i++) { ll l=Bin(s[i].l,k,x); ll r=Bin(s[i].r,k,x); if(l<=r) Update(l,r,s[i].flag,0,k-1,1); ans=max(ans,cover[1]); } printf("%I64d\n",ans); } return 0; }
hdu 5091 Beam Cannon 离散化+扫描线+线段树
原文地址:http://blog.csdn.net/u013532224/article/details/45508503