poj3924
题目:给定一个起点(xw1, yw1),直线经过(xw2, yw2),速度为vw无限运动的点,还有一个起点(xt1, yt1),终点(xt2, yt2),并且在以vt速度在两者往返运动,求两者在运动中的最近距离。。如果小于给定的dl,输出Dangerous,大于du输出Miss,否则输出perfect。。
思路:
ACM2008北京赛区的计算几何题,也是dyf神犇violet系列的一道题。。
思路不是很难,以xw点为参考系,那么题目就变成了求某个点及一些折线的最近距离。。
而且这些折线可以分成两组平行线段,每组可以分别求。
至于怎么求,可以用dyf神犇的数学方法。。(可能我太弱了,写完后一直错挑了半天就直接弃疗了)
我最后用的是直接三分线段,写起来好写一点。。
有什么不明白的可以看dyf博客。。写的很清楚。。
code:
#include<cstdio>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<algorithm>
#include<string>
#include<map>
#include<set>
#include<vector>
#include<queue>
#include<stack>
#include<ctime>
#include<utility>
#define M0(x) memset(x, 0, sizeof(x))
#define eps 1e-8
#define pi acos(-1.0)
using namespace std;
inline int sgn(const double& x){
return (x > eps) - (x < -eps);
}
struct point{
double x, y;
point(){}
point(double _x, double _y):x(_x), y(_y){}
void input(){
scanf("%lf%lf", &x, &y);
}
double len()const{
return sqrt(x * x + y * y);
}
point trunc(double l)const{
double r = l / len();
return point(r * x, r * y);
}
point rotate_left()const{
return point(-y, x);
}
point operator-(const point& p1)const{
return point(x - p1.x, y - p1.y);
}
point operator+(const point& p1)const{
return point(x + p1.x, y + p1.y);
}
bool operator==(const point& p1)const{
return sgn(x - p1.x) == && sgn(y - p1.y) == ;
}
double operator*(const point& p1)const{
return x * p1.y - y * p1.x;
}
double operator^(const point& p1)const{
return x * p1.x + y * p1.y;
}
point operator*(const double& l) const{
return point(x *l , y * l);
}
void out(){
printf("%.2f %.2f\n", x, y);
}
} p[], p2[], v[], zero(, );
double di, du, vnow; double get_distance(const point &p, const point &p1, const point &p2){
if (sgn((p2 - p1) ^ (p - p1)) <= ) return (p - p1).len();
if (sgn((p1 - p2) ^ (p - p2)) <= ) return (p - p2).len();
return fabs((p1 - p) * (p2 - p)) / (p1 - p2).len();
} void init(){
p2[].input(), scanf("%lf", &vnow);
v[] =(p2[]-p[]).trunc(vnow);
p[].input(), p2[].input(), scanf("%lf", &vnow);
v[] = (p2[] - p[]).trunc(vnow);
p[] = p[] - p[], p2[] = p2[] - p[];
scanf("%lf%lf", &di, &du);
} double gao(const point& p0,const point& p1, const point& p2){
int l = , r = 0x3fffffff, ui, l1, r1;
point v = p2 - p0;
point p00, p11;
double dis1, dis2, ans = 1e20;
while (l + < r){
if (l + >= r){
ans = min(ans, get_distance(zero, p0 + v * l, p1 + v * l));
ans = min(ans, get_distance(zero, p0 + v * r, p1 + v * r));
if (l + == r)
ans = min(ans, get_distance(zero, p0 + v * (l+), p1 + v * (l+)));
break;
}
ui = (r - l + ) / ;
l1 = l + ui, r1 = r - ui;
dis1 = get_distance(zero, p0 + v * l1, p1 + v * l1);
dis2 = get_distance(zero, p0 + v * r1, p1 + v * r1);
if (dis1 < dis2) r = r1;
else l = l1; }
return ans;
} void solve(){
point v1 = v[] - v[], v2 = (v[] + v[]) * (-);
double t = (p2[] - p[]).len() / vnow;
point p0 = p[], p1 = p0 + v1 * t, p3 = p1 + v2 * t, p4 = p3 + v1 * t;
// p0.out(), p1.out(), p3.out(), p4.out();
double ans = gao(p0, p1, p3);
ans = min(gao(p1, p3, p4), ans);
if (ans < di - eps) puts("Dangerous");
else if (ans > du + eps) puts("Miss");
else puts("Perfect");
} int main(){
while (scanf("%lf%lf", &p[].x, &p[].y) != EOF){
init();
solve();
}
return ;
}
poj3924的更多相关文章
随机推荐
- 839A Arya and Bran
A. Arya and Bran time limit per test 1 second memory limit per test 256 megabytes input standard inp ...
- HDU_1142(最短路 + dfs)
Jimmy experiences a lot of stress at work these days, especially since his accident made working dif ...
- sql重复数据的过滤问题
有重复数据主要有一下几种情况: 1.存在两条完全相同的纪录 这是最简单的一种情况,用关键字distinct就可以去掉 example: select distinct * from table(表名) ...
- Lazarus的二维码解决方案
不解释,直接上图
- Windows使用SSH Secure Shell实现免密码登录CentOS
笔记来自:http://blog.csdn.net/jiangshouzhuang/article/details/50683049 1.在Windows上生成密钥找到Secure Shell Cli ...
- 进制转换(NOIP2000&NOIP水题测试(2017082301))
题目链接:进制转换 这题得明白其中的数学方法,明白后就不难了. 那么我们应该怎么计算呢? 其实也很简单. 我们依然采取辗转相除法. 但是,对于负的余数,我们需要进行一些处理. 我们怎么处理呢? 很简单 ...
- 清幽傲竹实现的kbmMWServer数据库联接失败重联(转载红鱼儿)
1.修改kbmMWUnidac单元的TkbmMWUNIDACConnection.InternalOpenConnection方法,加上: //支持unidac重联 ...
- substr()和substring()函数
区别:主要是两者的参数不同 功能:相似. substr :返回一个从指定位置开始的指定长度的子字符串 substring :返回位于 String 对象中指定位置的子字符串. 用法: stringva ...
- De Bruijn序列
最近文章中经常出现及De Bruijin 这个关键字,网上搜索了一下,记录下来. De Bruijn序列 (德布鲁因序列) 问题:能否构造一个长度为2的n次方的二进制环状串,使得二进制环状串中总共2的 ...
- 2019.01.21 bzoj3674: 可持久化并查集加强版(主席树+并查集)
传送门 题意:维护可持久化并查集,支持在某个版本连边,回到某个版本,在某个版本 询问连通性. 思路: 我们用主席树维护并查集fafafa数组,由于要查询历史版本,因此不能够用路径压缩. 可以考虑另外一 ...