首页 > 其他 > 详细

foj 2144 三位几何+区间覆盖

时间:2014-03-15 06:39:23      阅读:452      评论:0      收藏:0      [点我收藏+]

题目大意:一个人站在三维坐标系下的原点处用炮打蚊子,给出n个蚊子的起始坐标跟单位时间匀速移动的方向向量,距离他R以内的蚊子都可以打到,不过他也需要休息,没蚊子的时候也可以休息下。求他要起来多少次打蚊子。

 

bubuko.com,布布扣
#include <iostream>
#include <cstdio>
#include <cmath>
#include <algorithm>
using namespace std;
const int N = 100005;
const double eps = 1e-6;
const double Pi=acos(-1.0);

int n, cnt;
double R;

inline bool scan_d(double &ret)
{  //如果数据比较多,而输入的数值比较小就不用scanf而用这种输入方法,用scanf会超时
    char c; int sgn;  
    if(c = getchar(),c == EOF) return 0; //EOF  
    while(c != - && (c < 0 || c > 9)) c = getchar();  
    sgn = (c == -) ? -1 : 1;  
    ret = (c == -) ? 0 : (c - 0);  
    while(c=getchar(),c>=0&&c<=9) ret=ret*10+(c-0);  
    ret *= sgn;  
    return 1;  
} 

struct Point3
{
    double x, y, z;
    Point3(double x=0,double y=0,double z=0):x(x),y(y),z(z){}
    void get() { scan_d(x); scan_d(y); scan_d(z); }
};
 
struct Node
{
    double x, y;
}f[N];

double Dot(Point3 a,Point3 b){return a.x*b.x+a.y*b.y+a.z*b.z;}

inline double min(double a,double b){ return a-b>eps?b:a;}
inline double max(double a,double b){ return a-b>eps?a:b;}

void Deal(Point3 p, Point3 q) 
{
    double a=Dot(q,q);  
    double b=2*Dot(p,q);  
    double c =Dot(p,p)-R*R;  
    double t =b*b-4*a*c;  
    if (t < eps) return;  
    else if (fabs(t) < eps)
    {  
        double i = -b / (2.0 * a);  
        if (i < 0) return;  
        f[cnt].x = f[cnt].y = i;  
    }  
    else 
    {  
        double i = (-b + sqrt(t) ) / (2 * a);  
        double j = (-b - sqrt(t) ) / (2 * a);  
        if (i < -eps && j < -eps) return;  
        else if (i < -eps) i = 0;  
        else if (j < -eps) j = 0;  
        f[cnt].x = min(i, j);  
        f[cnt].y = max(i, j);  
    }  
    cnt++;  
} 
 
void Init() 
{
    cnt = 0;
    Point3 p, v;
    scanf("%d%lf", &n, &R);
    for (int i = 0; i < n; i++) 
    {
        p.get();v.get();
        Deal(p, v);
    }
}
 
bool mycomp(const Node &a, const Node &b)
{
    if (fabs(a.y - b.y) > eps) return a.y - b.y < eps;
    return a.x - b.x < eps;
}
 
int Solve() 
{
    int i,ans = 0;
    double start = -1;
    for (i = 0; i < cnt; i++)
    {
        if (f[i].x - start > eps)
        {
            start = f[i].y;
            ans++;
        }
    }
    return ans;
}
 
int main ()
{
    int i,Icas;
    scanf("%d", &Icas);
    for (i = 1; i <= Icas; i++)
    {
        Init();
        sort(f, f + cnt, mycomp);
        printf("Case %d: %d %d\n", i, cnt, Solve());
    }
    return 0;
}
bubuko.com,布布扣

foj 2144 三位几何+区间覆盖,布布扣,bubuko.com

foj 2144 三位几何+区间覆盖

原文:http://www.cnblogs.com/xiong-/p/3601169.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!