您的位置:首页 > 其它

bzoj1199: [HNOI2005]汤姆的游戏

2017-04-06 11:45 337 查看
传送门

题目数据范围是250000.

敢n^2暴力吗?

正解:n^2暴力。

对第一维二分,暴力判第二维就行了。

本题已收入n^2能过的好题中。

#include<cstring>
#include<cmath>
#include<cstdio>
#include<iostream>
#include<cstdlib>
#include<algorithm>
#define eps 1e-8
using namespace std;
struct circle{
double x,y,r;
}a[250005];
struct square{
double x1,y1,x2,y2;
}b[250005];
struct point{
double x,y;
int id;
}c[250005];
int ans[250005],n,m,p,q,cir,squ;
double x,y,xx,yy;
char s[2];
bool cmp(point a,point b){
if (fabs(a.x-b.x)<eps) return a.y<b.y;
return a.x<b.x;
}
int ef1(double x){
int l=1,r=m,mid;
if (x>c[m].x-eps) return m+1;
while (l<r){
mid=(l+r)/2;
if (c[mid].x<=x) l=mid+1; else r=mid;
}
return l;
}
int ef2(double x){
int l=1,r=m,mid;
if (x<c[1].x+eps) return 0;
while (l<r){
mid=(l+r+1)/2;
if (c[mid].x>=x) r=mid-1; else l=mid;
}
return l;
}
int main(){
scanf("%d%d",&n,&m);
for (int i=1;i<=n;i++){
scanf("%s",&s);
if (s[0]=='c'){
cir++;
scanf("%lf%lf%lf",&a[cir].x,&a[cir].y,&a[cir].r);
}
else{
squ++;
scanf("%lf%lf%lf%lf",&x,&y,&xx,&yy);
b[squ].x1=min(x,xx);
b[squ].x2=max(x,xx);
b[squ].y1=min(y,yy);
b[squ].y2=max(y,yy);
}
}
for (int i=1;i<=m;i++){
scanf("%lf%lf",&c[i].x,&c[i].y);
c[i].id=i;
}
sort(c+1,c+m+1,cmp);
for (int i=1;i<=squ;i++){
p=ef1(b[i].x1);
q=ef2(b[i].x2);
for (int j=p;j<=q;j++)
if (c[j].y>b[i].y1+eps&c[j].y<b[i].y2-eps) ans[c[j].id]++;
}
for (int i=1;i<=cir;i++){
p=ef1(a[i].x-a[i].r);
q=ef2(a[i].x+a[i].r);
for (int j=p;j<=q;j++)
if ((c[j].x-a[i].x)*(c[j].x-a[i].x)+(c[j].y-a[i].y)*(c[j].y-a[i].y)<a[i].r*a[i].r) ans[c[j].id]++;
}
for (int i=1;i<=m;i++) printf("%d\n",ans[i]);
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: