4818 Largest Empty Circle on a Segment (几何+二分)
挺水的一道题,直接二分圆的半径即可。1y~
类似于以前半平面交求核的做法,假设半径已经知道,我们只需要求出线段周围哪些位置是不能放置圆心的即可。这样就转换为圆与直线,直线与直线交的问题了。
不知道这题能不能SAA过,有空试下。
代码如下:
#include <cmath>
#include <vector>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm> using namespace std; const double EPS = 1e-;
inline int sgn(double x) { return (x > EPS) - (x < -EPS);}
typedef pair<double, double> Point;
#define x first
#define y second
template<class T> T sqr(T x) { return x * x;}
Point operator + (Point a, Point b) { return Point(a.x + b.x, a.y + b.y);}
Point operator - (Point a, Point b) { return Point(a.x - b.x, a.y - b.y);}
Point operator * (Point a, double p) { return Point(a.x * p, a.y * p);}
Point operator / (Point a, double p) { return Point(a.x / p, a.y / p);} inline double cross(Point a, Point b) { return a.x * b.y - a.y * b.x;}
inline double dot(Point a, Point b) { return a.x * b.x + a.y * b.y;}
inline double veclen(Point a) { return sqrt(dot(a, a));}
inline Point vecunit(Point a) { return a / veclen(a);}
inline Point normal(Point a) { return Point(-a.y, a.x) / veclen(a);} struct Line {
Point s, t;
Line() {}
Line(Point s, Point t) : s(s), t(t) {}
Point vec() { return t - s;}
Point point(double p) { return s + vec() * p;}
Line move(double p) { // + left - right
Point nor = normal(vec());
return Line(s + nor * p, t + nor * p);
}
} ; inline bool between(Point o, Point a, Point b) { return sgn(dot(a - o, b - o)) < ;}
inline bool between(Point a, Line l) { return between(a, l.s, l.t);}
inline Point llint(Line a, Line b) { return a.point(cross(b.vec(), a.s - b.s) / cross(a.vec(), b.vec()));} bool clint(Point a, double r, double *sol) {
if (sgn(r - fabs(a.y)) <= ) return ;
double d = sqrt(sqr(r) - sqr(a.y));
//cout << "d " << d << endl;
sol[] = a.x - d;
sol[] = a.x + d;
return ;
} Line Y0 = Line(Point(, ), Point(, )); double L;
inline void adjust(double &x) { x = max(0.0, min(L, x));}
Point getseg(Line a, double r) {
vector<double> sol;
sol.clear();
double t[];
if (clint(a.s, r, t)) sol.push_back(t[]), sol.push_back(t[]);
if (clint(a.t, r, t)) sol.push_back(t[]), sol.push_back(t[]);
Line l1 = a.move(r), l2 = a.move(-r), l3 = Line(l1.s, l2.s), l4 = Line(l1.t, l2.t);
Point p1 = llint(l1, Y0), p2 = llint(l2, Y0), p3 = llint(l3, Y0), p4 = llint(l4, Y0);
if (between(p1, l1)) sol.push_back(p1.x);
if (between(p2, l2)) sol.push_back(p2.x);
if (between(p3, l3)) sol.push_back(p3.x);
if (between(p4, l4)) sol.push_back(p4.x);
if (sol.size() == ) return Point(-, -);
sort(sol.begin(), sol.end());
//cout << "sol ";
//for (int i = 0; i < sol.size(); i++) cout << sol[i] << ' '; cout << endl;
adjust(sol[]), adjust(sol[sol.size() - ]);
return Point(sol[], sol[sol.size() - ]);
} const int N = ;
typedef pair<double, int> Event;
Line l[N];
int n; bool test(double r) {
vector<Event> ev;
ev.clear();
for (int i = ; i < n; i++) {
Point tmp = getseg(l[i], r);
if (tmp.x < || tmp.y < ) continue;
//cout << tmp.x << '~' << tmp.y << endl;
ev.push_back(Event(tmp.x, ));
ev.push_back(Event(tmp.y, -));
}
sort(ev.begin(), ev.end());
//cout << r << endl;
//for (int i = 0; i < ev.size(); i++) cout << ev[i].x << '&' << ev[i].y << ' '; cout << endl;
double last = ;
int cnt = , sz = ev.size();
for (int i = ; i < sz; i++) {
if (ev[i].y == ) {
if (cnt == && sgn(ev[i].x - last) > ) return ;
cnt++;
} else {
if (cnt == ) last = ev[i].x;
cnt--;
}
}
return sgn(L - last) > ;
} int main() {
//freopen("in", "r", stdin);
int T;
cin >> T;
while (T-- && cin >> n >> L) {
for (int i = ; i < n; i++) cin >> l[i].s.x >> l[i].s.y >> l[i].t.x >> l[i].t.y;
double lp = , rp = , mp;
while (rp - lp > EPS) {
mp = (lp + rp) / ;
if (test(mp)) lp = mp;
else rp = mp;
}
//puts("~~~~~~~~~~~~~~~~~~~~~~~~");
//test(2.118);
printf("%.3f\n", mp);
}
return ;
}
——written by Lyon
4818 Largest Empty Circle on a Segment (几何+二分)的更多相关文章
- uva 1463 - Largest Empty Circle on a Segment(二分+三分+几何)
题目链接:uva 1463 - Largest Empty Circle on a Segment 二分半径,对于每一个半径,用三分求出线段到线段的最短距离,依据最短距离能够确定当前R下每条线段在[0 ...
- UVALive 4818 - Largest Empty Circle on a Segment (计算几何)
题目链接:https://icpcarchive.ecs.baylor.edu/index.php?option=com_onlinejudge&Itemid=8&page=show_ ...
- Project Euler 363 Bézier Curves(几何+二分)
题目链接: https://projecteuler.net/problem=363 题目: A cubic Bézier curve is defined by four points: \(P_0 ...
- BZOJ-1822 Frozen Nova 冷冻波 计(jie)算(xi)几何+二分+最大流判定+经典建图
这道逼题!感受到了数学对我的深深恶意(#‵′).... 1822: [JSOI2010]Frozen Nova 冷冻波 Time Limit: 10 Sec Memory Limit: 64 MB S ...
- UVALive - 6856 Circle of digits 后缀数组+二分
题目链接: http://acm.hust.edu.cn/vjudge/problem/82135 Circle of digits Time Limit: 3000MS 题意 把循环串分割成k块,让 ...
- 【BZOJ1822】[JSOI2010]Frozen Nova 冷冻波 几何+二分+网络流
[BZOJ1822][JSOI2010]Frozen Nova 冷冻波 Description WJJ喜欢“魔兽争霸”这个游戏.在游戏中,巫妖是一种强大的英雄,它的技能Frozen Nova每次可以杀 ...
- Aquarium Tank(csu1634+几何+二分)Contest2087 - 湖南多校对抗赛(2015.05.24)-G
Aquarium Tank Time Limit: 1 Sec Memory Limit: 128 MBSubmit: 15 Solved: 4[Submit][Status][Web Board ...
- poj 2002 Squares 几何二分 || 哈希
Squares Time Limit: 3500MS Memory Limit: 65536K Total Submissions: 15137 Accepted: 5749 Descript ...
- Visulalize Boost Voronoi in OpenSceneGraph
Visulalize Boost Voronoi in OpenSceneGraph eryar@163.com Abstract. One of the important features of ...
随机推荐
- sass进阶
代码的重用 基础的部分我们讲述了变量 Mixin 这两种方法可以增加扩展和重用 现在开始继续学习:extend继承 .class1 { border: 1px solid #ddd; } .class ...
- CodeChef--Cards, bags and coins
题目链接 Yet another game from chef. Chef gives you N cards and M bags. Each of the N cards has an integ ...
- spring boot指定外部配置的坑
外部配置文件所在目录path/to/dir 指定--spring.config.location=path/to/dir 项目启动,没有使用任何配置文件,项目外和jar包中的都没有使用 这是因为其把p ...
- “本地视频使用flashFXP上传虚拟服务器“的方法
一.视频转换格式 首先,想要在网页中直接嵌入视频,就得用video标签,而<video>支持的仅有的几种格式中,MP4是兼容性,通用性各方面相对友好的,所以,建议上传之前先转换格式并压缩. ...
- eclipse 代码格式化快捷键CTRL SHIFT F无反应的解决办法
基本上就是被其他软件占用了,比如输入法的简繁体切换,改其他软件,保留eclipse就好
- 使用Jest进行单元测试
Jest是Facebook推出的一款单元测试工具. 安装 npm install --save-dev jest ts-jest @types/jest 在package.json中添加脚本: “te ...
- python 内置操作函数
- 洛谷P1456Monkey King
洛谷P1456 Monkey King 题目描述 Once in a forest, there lived N aggressive monkeys. At the beginning, they ...
- 低价替代Vector CANoe CAN总线适配解决方案支持所有USBCAN(周立功CAN、PCAN、Kvaser、ValueCAN、NI CAN)
在汽车通信领域CAN总线使用非常广泛,最强大的工具有Vector Case(10WRMB).Pcan(2KRMB),ZLGCAN(1.5KRMB),KVASER(2KRMB).ValueCAN(4KR ...
- JavaScript--location.href的跳转
页面重载 true 强制从服务器加载 false 优先从缓存加载 window.location.reload(true); window.location.href.self.location. ...