[APIO2018] Circle selection 选圆圈
Description
给出 \(n\) 个圆 \((x_i,y_i,r_i)\)
每次重复以下步骤:
找出半径最大的圆,并删除与这个圆相交的圆
求出每一个圆是被哪个圆删除的
Solution
\(kd-tree\) 搞一下
维护能够围住所有圆的最小矩形
然后模拟题意,枚举半径最大的圆
查询时就判断询问的圆是否与这个矩形有交,有交就递归下去
#include<bits/stdc++.h>
#define sqr(x) ((x)*(x))
using namespace std;
template<class T>void gi(T &x){
int f;char c;
for(f=1,c=getchar();c<'0'||c>'9';c=getchar())if(c=='-')f=-1;
for(x=0;c<='9'&&c>='0';c=getchar())x=x*10+(c&15);x*=f;
}
const int N=3e5+10,inf=2e9+10;const double eps=1e-7;
int n,rt,D,ans[N];
struct data{
double a[2],mn[2],mx[2],R;int l,r,tag,id;
inline double& operator [](int x){return a[x];}
}t[N],c[N],W;
inline bool operator <(data p,data q){return p[D]<q[D];}
inline bool comp(data p,data q){return p.R!=q.R?p.R>q.R:p.id<q.id;}
inline void upd(int o){
int l=t[o].l,r=t[o].r;
for(int i=0;i<2;i++){
t[o].mx[i]=-inf;t[o].mn[i]=inf;
if(!t[o].tag)t[o].mn[i]=min(t[o].mn[i],t[o].a[i]-t[o].R),
t[o].mx[i]=max(t[o].mx[i],t[o].a[i]+t[o].R);
if(l)t[o].mn[i]=min(t[o].mn[i],t[l].mn[i]),
t[o].mx[i]=max(t[o].mx[i],t[l].mx[i]);
if(r)t[o].mn[i]=min(t[o].mn[i],t[r].mn[i]),
t[o].mx[i]=max(t[o].mx[i],t[r].mx[i]);
}
}
inline int build(int l,int r,int k){
int mid=(l+r)>>1,o=mid;D=k;
nth_element(t+l,t+mid,t+r+1);
if(l<mid)t[o].l=build(l,mid-1,k^1);
if(r>mid)t[o].r=build(mid+1,r,k^1);
return upd(o),o;
}
inline void query(int o){
if(!o)return ;
for(int i=0;i<2;i++)
if(W.a[i]-W.R>t[o].mx[i] || W.a[i]+W.R<t[o].mn[i])return ;
if(!t[o].tag){
double dis=0,R=sqr(W.R+t[o].R);
for(int i=0;i<2;i++)dis+=sqr(t[o].a[i]-W.a[i]);
if(dis-R<eps)ans[t[o].id]=W.id,t[o].tag=1;
}
query(t[o].l);query(t[o].r);
}
int main(){
freopen("pp.in","r",stdin);
freopen("pp.out","w",stdout);
cin>>n;
double x,y,z;
for(int i=1;i<=n;i++){
gi(x);gi(y);gi(z);
t[i].a[0]=c[i].a[0]=x;t[i].a[1]=c[i].a[1]=y;
t[i].R=c[i].R=z;c[i].id=t[i].id=i;
}
rt=build(1,n,0);
sort(c+1,c+n+1,comp);
for(int i=1;i<=n;i++){
if(ans[c[i].id])continue;
W=c[i];
query(rt);
}
for(int i=1;i<=n;i++)printf("%d ",ans[i]);
return 0;
}
[APIO2018] Circle selection 选圆圈的更多相关文章
- 【LG4631】[APIO2018]Circle selection 选圆圈
[LG4631][APIO2018]Circle selection 选圆圈 题面 洛谷 题解 用\(kdt\)乱搞剪枝. 维护每个圆在\(x.y\)轴的坐标范围 相当于维护一个矩形的坐标范围为\([ ...
- [APIO2018] Circle selection 选圆圈(假题解)
题面 自己去\(LOJ\)上找 Sol 直接排序然后\(KDTree\)查询 然后发现\(TLE\)了 然后把点旋转一下,就过了.. # include <bits/stdc++.h> # ...
- [Luogu4631][APIO2018] Circle selection 选圆圈
Luogu 题目描述 在平面上,有 \(n\) 个圆,记为 \(c_1, c_2,...,c_n\) .我们尝试对这些圆运行这个算法: \(1\).找到这些圆中半径最大的.如果有多个半径最大的圆,选择 ...
- luogu P4631 [APIO2018] Circle selection 选圆圈
传送门 那个当前半径最大的圆可以用堆维护.这道题一个想法就是优化找和当前圆有交的圆的过程.考虑对于所有圆心建KD-tree,然后在树上遍历的找这样的点.只要某个点子树内的点构成的矩形区域到当前圆心的最 ...
- 洛谷4631 [APIO2018] Circle selection 选圆圈 (KD树)
qwq纪念AC450 一开始想这个题想复杂了. 首先,正解的做法是比较麻烦的. qwqq 那么就不如来一点暴力的东西,看到平面上点的距离的题,不难想到\(KD-Tree\) 我们用类似平面最近点对那个 ...
- [APIO2018]Circle selection
https://www.zybuluo.com/ysner/note/1257597 题面 在平面上,有\(n\)个圆,记为\(c_1,c_2,...,c_n\).我们尝试对这些圆运行这个算法: 找到 ...
- 【APIO2018】选圆圈(平面分块 | CDQ分治 | KDT)
Description 给定平面上的 \(n\) 个圆,用三个参数 \((x, y, R)\) 表示圆心坐标和半径. 每次选取最大的一个尚未被删除的圆删除,并同时删除所有与其相切或相交的圆. 最后输出 ...
- 「APIO2018选圆圈」
「APIO2018选圆圈」 题目描述 在平面上,有 \(n\) 个圆,记为 \(c_1, c_2, \ldots, c_n\) .我们尝试对这些圆运行这个算法: 找到这些圆中半径最大的.如果有多个半径 ...
- 【LOJ2586】【APIO2018】选圆圈 CDQ分治 扫描线 平衡树
题目描述 在平面上,有 \(n\) 个圆,记为 \(c_1,c_2,\ldots,c_n\) .我们尝试对这些圆运行这个算法: 找到这些圆中半径最大的.如果有多个半径最大的圆,选择编号最小的.记为 \ ...
随机推荐
- C语言编程学习:使用函数必须知道的3点注意事项
C语言是面向过程的,而C++是面向对象的 C和C++的区别: C是一个结构化语言,它的重点在于算法和数据结构.C程序的设计首要考虑的是如何通过一个过程,对输入(或环境条件)进行运算处理得到输出(或实现 ...
- Qt自动填写表单并点击按钮,包括调用js方法
本篇博客参阅了很多其他大牛的文章,具体找不到了,还望包涵>_< 因为其他博客大都是只有主要代码,对于像我这种菜鸟,根本摸不着头脑,以此想总结一下,帮助新手尽快实现功能... 主要是调用了C ...
- python中readline判断文件读取结束的方法
注:内容来自网络 本文实例讲述了python中readline判断文件读取结束的方法.分享给大家供大家参考.具体分析如下: 大家知道,python中按行读取文件可以使用readline函数,下面现介绍 ...
- 2017qcon大会的一点想法(安全人才如何不被淘汰?)
2017 qcon 上海专门设立了“直击黑产,业务安全的攻与防”专题,通过这次专题的了解和学习,让我对黑产的攻防有了更深入认识. 1. 安全防护趋势 2017 qcon 上海专门设立了“直击黑产,业务 ...
- EXPORT Man Information for Linux use COMMAND col
col命令 是一个标准输入文本过滤器,它从标注输入设备读取文本内容,并把内容显示到标注输出设备.在许多UNIX说明文件里,都有RLF控制字符.当我们运用shell特殊字符>和>>,把 ...
- JMeter—断言
断言用来对服务器的响应数据做验证,常用的断言是响应断言,支持正则表达式. 一.BeanShell Assertion 用来访问JMeter的属性: log对象,可以利用此对象写日志 SampleRes ...
- python3的enumerate函数
enumerate() 函数用于将一个可遍历的数据对象(如列表.元组或字符串)组合为一个索引序列,同时列出数据和数据下标,一般用在 for 循环当中.
- POJ3666 Making the Grade
POJ3666 Making the Grade 题意: 给定一个长度为n的序列A,构造一个长度为n的序列B,满足b非严格单调,并且最小化S=∑i=1N |Ai-Bi|,求出这个最小值S,1<= ...
- luogu3292 [SCOI2016]幸运数字
link 题目大意:给一棵树,每个点有个权值,N<=2万 20万次询问,每次询问查询某两个点路径上所有点的权值xjb异或的最大值 首先看到xjb异或就可以断定是线性基了 并且由于这是树上问题我们 ...
- jupyter notebook不小心点了退出,怎么找到密码
在cmd中输入:jupyter notebook list 回车 在输出的内容中找"token=xxxxxxxxx",把等号后面一大堆的东西输入到 password or to ...