poj2194Stacking Cylinders

链接

可以根据反余弦和反正切算出角a和b的值, 然后向量旋转就可以了,图中的状态旋转rotate((2,0),a+b)  反状态把角度反过来,点取(-2,0)即可。

不知道是不是理解错了,题意写着两圆距离》2,《3.4,在求得时候就加了特判,一直WA。。。去了特判就过了。

为了提高精度,可以全化为atan2.

  1 #include <iostream>
  2 #include<cstdio>
  3 #include<cstring>
  4 #include<algorithm>
  5 #include<stdlib.h>
  6 #include<vector>
  7 #include<cmath>
  8 #include<queue>
  9 #include<set>
 10 using namespace std;
 11 #define N 100000
 12 #define LL long long
 13 #define INF 0xfffffff
 14 const double eps = 1e-10;
 15 const double pi = acos(-1.0);
 16 const double inf = ~0u>>2;
 17 const double r = 1.0;
 18 const double rd = 3.40;
 19 struct point
 20 {
 21     double x,y,r;
 22     point(double x=0,double y=0):x(x),y(y){}
 23 }p[N],q[N];
 24 typedef point pointt;
 25 pointt operator -(point a,point b)
 26 {
 27     return point(a.x-b.x,a.y-b.y);
 28 }
 29 double dis(point a)
 30 {
 31     return sqrt(a.x*a.x+a.y*a.y);
 32 }
 33 double dot(point a,point b)
 34 {
 35     return a.x*b.x+a.y*b.y;
 36 }
 37 double angle(point a,point b)
 38 {
 39     return acos(dot(a,b)/dis(a)/dis(b));
 40 }
 41 double angle1(point v)
 42 {
 43     return atan2(v.y,v.x);
 44 }
 45 int dcmp(double x)
 46 {
 47     if(fabs(x)<eps) return 0;
 48     return x<0?-1:1;
 49 }
 50 point rotate(point a,double rad)//逆时针旋转
 51 {
 52     return point(a.x*cos(rad)-a.y*sin(rad),a.x*sin(rad)+a.y*cos(rad));
 53 }
 54 bool cmp(point a,point b)
 55 {
 56     return a.x<b.x;
 57 }
 58 int main()
 59 {
 60     int n,i,j;
 61     while(scanf("%d",&n)&&n)
 62     {
 63         for(i = 1; i <= n;i++)
 64         {
 65             double x;
 66             scanf("%lf",&x);
 67             p[i] = point(x,1);
 68         }
 69         sort(p+1,p+n+1,cmp);
 70         int tn = n;
 71         double maxz = 0;
 72         point tp;
 73         while(1)
 74         {
 75             int g = 0;
 76             for(i = 1; i < tn; i++)
 77             {
 78                 if(maxz<p[i].y)
 79                 {
 80                     maxz = p[i].y;
 81                     tp = p[i];
 82                 }
 83                // if(dcmp(dis(p[i]-p[i+1])-2*r)<0) continue;
 84                // if(dcmp(dis(p[i]-p[i+1])-rd)>0) continue;
 85 
 86                 double b = atan2(fabs(p[i].y-p[i+1].y),fabs(p[i].x-p[i+1].x));
 87                 double d = dis(p[i]-p[i+1])/2;
 88                 double dd = sqrt(4-(d*d));
 89                 double a = atan2(dd,d);
 90                 if(dcmp(a+b-pi/2.0)>0) continue;
 91                 if(p[i].y<p[i+1].y)
 92                 {
 93                     point pp = point(2.0,0);
 94                     q[++g] = rotate(pp,a+b);
 95                     q[g] = point(q[g].x+p[i].x,q[g].y+p[i].y);
 96                 }
 97                 else
 98                 {
 99                     point pp = point(-2,0);
100                     q[++g] = rotate(pp,-a-b);
101                     q[g] = point(q[g].x+p[i+1].x,q[g].y+p[i+1].y);
102                 }
103             }
104             if(maxz<p[tn].y)
105             {
106                 maxz  = p[tn].y;
107                 tp = p[tn];
108             }
109             if(!g) break;
110             tn = g;
111             for(i = 1; i <= g ; i++)
112             p[i] = q[i];
113         }
114         printf("%.4f %.4f\n",tp.x,tp.y);
115     }
116     return 0;
117 }
View Code

 

posted @ 2014-08-09 16:09  _雨  阅读(210)  评论(0编辑  收藏  举报