码迷,mamicode.com
首页 > 其他好文 > 详细

HDU 3492 (直线与所有线段相交) Segment

时间:2014-11-26 22:29:41      阅读:270      评论:0      收藏:0      [点我收藏+]

标签:style   blog   http   io   ar   color   os   sp   for   

题意:

给出n个线段,判断是否存在一条直线使得所有线段在直线上的射影的交非空。

分析:

如果我们找到一条与所有线段相交的直线,然后做一条与该直线垂直的直线,这些线段在直线上的射影就一定包含这个垂足。

所以我们只要判断是否存在一条直线与所有的点相交即可。

如果存在这样一条直线,那么将这条直线平移或者旋转,就会被这些线段中的某两个端点“卡”住。

所以我们枚举两个端点,然后判断这些线段是否与这两个点所在的直线都相交即可。

 

本以为是一道很简单的计算几何,结果卡了好几天。

看了别人的题解,才发现问题所在。

http://www.cppblog.com/acronix/archive/2010/08/17/123765.html

因为有可能存在重点,所以要判断,弄了个标志变量issame,如果所有的点都是同一个点那么也应该输出Yes

bubuko.com,布布扣
 1 #include <cstdio>
 2 #include <cmath>
 3 
 4 const int maxn = 600 + 10;
 5 const double eps = 1e-8;
 6 struct Point
 7 {
 8     double x, y;
 9     Point(double x=0, double y=0):x(x), y(y) {}
10 }p[maxn];
11 int dcmp(double x)
12 {
13     if(fabs(x) < eps) return 0;
14     return x < 0 ? -1 : 1;
15 }
16 
17 Point operator - (const Point& a, const Point& b)
18 { return Point(a.x-b.x, a.y-b.y); }
19 
20 double Cross(const Point& a, const Point& b)
21 { return (a.x*b.y - a.y*b.x); }
22 
23 bool operator == (const Point& a, const Point& b)
24 { return dcmp(a.x-b.x) == 0 && dcmp(a.y-b.y) == 0; }
25 
26 bool intersect(const Point& a, const Point& b, const Point& p1, const Point& p2)
27 {
28     int d1 = dcmp(Cross(b-a, p1-a));
29     int d2 = dcmp(Cross(b-a, p2-a));
30     if(d1 == 0 || d2 == 0) return true;
31     if(d1 * d2 < 0) return true;
32     return false;
33 }
34 
35 int main(void)
36 {
37     //freopen("3492in.txt", "r", stdin);
38     int T;
39     scanf("%d", &T);
40     while(T--)
41     {
42         int n;
43         scanf("%d", &n);
44         for(int i = 0; i < 2*n-1; i += 2)
45             scanf("%lf%lf%lf%lf", &p[i].x, &p[i].y, &p[i+1].x, &p[i+1].y);
46         
47         bool exist = false;
48         bool issame = true;
49         for(int i = 0; i < 2*n-1 && !exist; ++i)
50         {
51             for(int j = i+1; j < 2*n && !exist; ++j)
52             {
53                 if(p[i] == p[j]) continue;
54                 issame = false;
55                 int k;
56                 for(k = 0; k < 2*n; k += 2)
57                     if(!intersect(p[i], p[j], p[k], p[k+1])) break;
58                 if(k == 2 * n)
59                     exist = true;
60             }
61         }
62         
63         if(exist || issame) puts("Yes");
64         else puts("No");
65     }
66     
67     return 0;
68 } 
代码君

 

HDU 3492 (直线与所有线段相交) Segment

标签:style   blog   http   io   ar   color   os   sp   for   

原文地址:http://www.cnblogs.com/AOQNRMGYXLMV/p/4124942.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!