【CF887E】Little Brother

题意:给你n个圆和一条线段,保证圆和圆、圆和线段所在直线不相交,不相切,不包含。求一个过线段两端点的圆,满足不和任何圆相交(可以相切、包含)。问圆的最小半径。

n<=100000

题解:比较显然的二分题。由于新圆的半径一定在线段的中垂线上,且距离越远半径越大。那么问题就变成了最小化半径到线段的距离。

不难发现,对于每个圆来说,如果新圆不和它相交,那么半径所在的区域会被限定在$(-\infty,a]\bigcup[b,\infty)$里。a和b我们可以通过二分求得。最后用扫描线统计出所有合法的半径区间,并更新答案即可。

  1. #include <cstdio>
  2. #include <cstring>
  3. #include <iostream>
  4. #include <algorithm>
  5. #include <cmath>
  6. using namespace std;
  7. const int maxn=100010;
  8. struct point
  9. {
  10. double x,y;
  11. point() {}
  12. point(double a,double b) {x=a,y=b;}
  13. point operator + (const point &a) const {return point(x+a.x,y+a.y);}
  14. point operator - (const point &a) const {return point(x-a.x,y-a.y);}
  15. point operator * (const double &a) const {return point(x*a,y*a);}
  16. double operator * (const point &a) const {return x*a.y-y*a.x;}
  17. }A,B,P,C,D,O,K,K1;
  18. int n,m,sum;
  19. double R,ans;
  20. struct node
  21. {
  22. double x; int k;
  23. node() {}
  24. node(double a,int b) {x=a,k=b;}
  25. }q[maxn<<1];
  26. inline double dis(point a) {return sqrt(a.x*a.x+a.y*a.y);}
  27. inline int rd()
  28. {
  29. int ret=0,f=1; char gc=getchar();
  30. while(gc<'0'||gc>'9') {if(gc=='-') f=-f; gc=getchar();}
  31. while(gc>='0'&&gc<='9') ret=ret*10+(gc^'0'),gc=getchar();
  32. return ret*f;
  33. }
  34. bool cmp(const node &a,const node &b)
  35. {
  36. return a.x<b.x;
  37. }
  38. int main()
  39. {
  40. double l,r,mid;
  41. A.x=rd(),A.y=rd(),B.x=rd(),B.y=rd(),n=rd(),C=(A+B)*0.5,K=B-A;
  42. K=K*(1.0/dis(K)),K1=point(-K.y,K.x);
  43. int i,j,flag;
  44. for(i=1;i<=n;i++)
  45. {
  46. P.x=rd(),P.y=rd(),R=rd();
  47. flag=((P-A)*(B-P)>0);
  48. l=-1e12,r=1e12;
  49. for(j=1;j<=80;j++)
  50. {
  51. mid=(l+r)/2,O=C+(K1*mid);
  52. if((dis(P-O)>dis(A-O)+R)^flag) l=mid;
  53. else r=mid;
  54. }
  55. q[++m]=node(l,flag?-1:1);
  56. l=-1e12,r=1e12;
  57. for(j=1;j<=80;j++)
  58. {
  59. mid=(l+r)/2,O=C+(K1*mid);
  60. if((dis(A-O)>dis(P-O)+R)^flag) r=mid;
  61. else l=mid;
  62. }
  63. q[++m]=node(r,flag?1:-1);
  64. }
  65. q[++m]=node(1e12,0),q[++m]=node(-1e12,0),q[++m]=node(0,0);
  66. sort(q+1,q+m+1,cmp);
  67. ans=1e12;
  68. for(flag=0,i=1;i<=m;i++)
  69. {
  70. if(!sum) flag=1,ans=min(ans,fabs(q[i].x));
  71. sum+=q[i].k;
  72. if(!sum) flag=1,ans=min(ans,fabs(q[i].x));
  73. }
  74. if(!flag) puts("-1");
  75. else O=C+(K1*ans),printf("%.10lf",dis(A-O));
  76. return 0;
  77. }//2 4 7 13 3 3 0 1 12 4 2 -4 14 2

【CF887E】Little Brother 二分+几何的更多相关文章

  1. hdu 4033 二分几何

    参考:http://blog.csdn.net/libin56842/article/details/26618129 题意:给一个正多边形内点到其他顶点的距离(逆时针给出),求正多边形的边长 二分多 ...

  2. 二分法 (UVA10668 Expanding Rods)(二分+几何)

    转载请注明出处:優YoU http://user.qzone.qq.com/289065406/blog/1301845324 大致题意: 一根两端固定在两面墙上的杆 受热弯曲后变弯曲.求前后两个状态 ...

  3. Incircle and Circumcircle(二分+几何)浙大月赛zoj3806(详解版)图

    Incircle and Circumcircle Time Limit: 2 Seconds Memory Limit: 65536 KB Special Judge A triangle is o ...

  4. 【CF744D】Hongcow Draws a Circle 二分+几何

    [CF744D]Hongcow Draws a Circle 题意:给你平面上n个红点和m个蓝点,求一个最大的圆,满足圆内不存在蓝点,且至少包含一个红点. $n,m\le 10^3$ 题解:我们先不考 ...

  5. Codeforces Round #409 (rated, Div. 2, based on VK Cup 2017 Round 2) A B C D 暴力 水 二分 几何

    A. Vicious Keyboard time limit per test 2 seconds memory limit per test 256 megabytes input standard ...

  6. 【BZOJ3007】拯救小云公主 二分+几何+对偶图

    [BZOJ3007]拯救小云公主 Description     英雄又即将踏上拯救公主的道路……     这次的拯救目标是——爱和正义的小云公主.     英雄来到boss的洞穴门口,他一下子就懵了 ...

  7. POJ 1905 题解(二分+几何)

    题面 传送门 分析 如图:已知AB=L,弧AB=L(1+nC)" role="presentation" style="position: relative;& ...

  8. poj 1905Expanding Rods

    /* 二分 + 几何 弧长L, 圆半径R, 弧度 q, L=R*q; 二分: 弧度(0~PI) 或者 高度(L/2~L) */ #include<cstdio> #include<i ...

  9. SDU暑假排位第一场 (Gym - 100889)

    啊今天有点挂机啊 D题和队友暴力后发现一组数据跑得飞快 然后遇上1e5组数据就没了..... 然后我疯狂优化暴力 然后去世了 最后半小时F也没写出来 主要还是最后有点慌并且没有考虑清楚 导致情况越写越 ...

随机推荐

  1. koa2使用注意点总结

    post请求,ajax传入的参数获取的时候为ctx.request.body get请求,ajax传入参数获取的时候为ctx.request.query.参数名 koa-csrf可以设置什么请求的时候 ...

  2. apt 之 最强技能:【欺骗】,文雅点【偷梁换柱】!

    apt这种软件包管理系统,有个最大特点是:只照本宣科,而不管实际情况. 所以,我们用户就可以利用这一点,来欺骗它,达到我们的目的. ------------------------------好了,现 ...

  3. mysql数据库2

    命令行客户端软件MySQL Command Line Client, 打开该程序,输入数据库密码,登陆到MySQL软件, 如果想通过该命令行工具来操作MySQL软件,只需要在"mysql&g ...

  4. 单例模式__new__

    单例模式,使用__new__ __new__是构造函数, __init__是初始化方法,先调用了__new__返回了实例,__init__给这个实例初始化绑定一些属性. class Singleton ...

  5. webdriver+expected_conditions二次封装

    结合这两种方法对代码做二次封装,可以提升脚本性能 例: #coding:utf-8 #封装元素方法from selenium import webdriverfrom selenium.webdriv ...

  6. Java动态调用类中方法

    在Java中,调用类的方法有两种方式:对于静态方法可以直接使用类名调用,对于非静态方法必须使用类的对象调用.反射机制提供了比较另类的调用方式,可以根据需要指定要调用的方法,而不必在编程时确定.调用的方 ...

  7. Linux+Redis实战教程_day01_常用命令【重点】

    3.常用命令[重点] Linux命令中参数,一般都是无序的.特殊情况下除外 3.1.磁盘管理命令 ls命令:列出目录内容 参数: -a 查询所有文件和文件夹.包含隐藏的 -l 查询详细列表    ls ...

  8. iOS Ad hoc

    There's one situation in which you need an Ad Hoc profile, and that's when you want to test Push Not ...

  9. MySQL用户认证及权限控制

    一.MySQL用户认证: 登录并不属于访问控制机制,而属于用户身份识别和认证: 1.用户名—user 2.密码—password 3.登录mysqld主机—host 实现用户登录MySQL,建立连接. ...

  10. 使用 urllib 发送请求

    urllib.request.urlopen(url, data=None, timeout=n) 用于发送HTTP请求并得到响应内容 In []: import urllib.request In ...