您的位置:首页 > 编程语言

[代码]ACM-ICPC 2012 Regionals Asia - Jinhua D Crazy Tank / HDU 4445

2012-11-04 18:54 477 查看

Abstract

ACM-ICPC 2012 Regionals Asia - Jinhua D Crazy Tank / HDU 4445

扫描线

Source

http://acm.hdu.edu.cn/showproblem.php?pid=4445

Solution

很多人是水过的,我贴个正经的扫描线的吧。

Code

#include <cassert>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <iostream>
#include <cmath>
using namespace std;

const double PI = acos(-1.0);
const double EPS = 1e-8;

inline int sgn(double x) {
if (fabs(x)<EPS) return 0;
return x>0?1:-1;
}

int N, M;
double l1, r1, l2, r2;
double v[222];
double g=9.8, h;

double calc(double v, double a) {
double vx = v*cos(a);
double vy = v*sin(a);
double delta = vy*vy+2*g*h;
delta = max(0.0, delta);
double t = (vy+sqrt(delta))/g;
return vx*t;
}

double tri(double l, double r, double v, double &d) {
int cnt = 100;
while (cnt--) {
double m1 = (l+r)/2;
double m2 = (m1+r)/2;
if (calc(v, m1)>calc(v, m2)) r = m2;
else l = m1;
}
d = calc(v, l);
return l;
}

double bin(double l, double r, double d, double v, bool up) {
int cnt = 100;
while (cnt--) {
double m = (l+r)/2;
if ((calc(v, m)<d)^up) l = m;
else r = m;
}
return l;
}

struct se {
double a;
bool in;
int cnt;
se() {}
se(double x, bool y, int z): a(x), in(y), cnt(z) {}
bool operator<(const se &rhs) const {
if (sgn(a-rhs.a)==0) {
return in<rhs.in;
}
return a<rhs.a;
}
}e[9999];

void ae(double a, bool in, int cnt) {
e[M++] = se(a, in, cnt);
}

void solve(double l, double r, double d, double v, double t, int cnt) {
if (sgn(d-l)<0) return;
if (sgn(d-r)<0) {
double hmr = bin(-PI/2, t, l, v, 0);
double mdk = bin(t, PI/2, l, v, 1);
if (sgn(hmr-mdk)>0) while (1) puts("");
ae(hmr, 0, cnt); ae(mdk, 1, -cnt);
return;
}
double s1 = bin(-PI/2, t, l, v, 0);
double t1 = bin(-PI/2, t, r, v, 0);
double s2 = bin(t, PI/2, r, v, 1);
double t2 = bin(t, PI/2, l, v, 1);
if (sgn(s1-t1)>0) while (1) puts("");
if (sgn(s2-t2)>0) while (1) puts("");
if (sgn(t1-s2)>=0) {
ae(s1, 0, cnt); ae(t2, 1, -cnt);
}
else {
ae(s1, 0, cnt); ae(t1, 1, -cnt);
ae(s2, 0, cnt); ae(t2, 1, -cnt);
}
}

char s[111];

int main() {
int i, j, k;
while (cin>>N>>h>>l1>>r1>>l2>>r2, N) {
M = 0;
for (i = 0; i < N; ++i) {
cin>>v[i];
double d, t;
t = tri(-PI/2, PI/2, v[i], d);
solve(l1, r1, d, v[i], t, 1);
solve(l2, r2, d, v[i], t, -998);
}
sort(e, e+M);
int ans = 0;
int cnt = 0;
for (i = 0; i < M; ++i) {
cnt += e[i].cnt;
if (cnt>N) while (1) puts("");
ans = max(ans, cnt);
}
printf("%d\n", ans);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: