poj2194Stacking Cylinders
可以根据反余弦和反正切算出角a和b的值, 然后向量旋转就可以了,图中的状态旋转rotate((2,0),a+b) 反状态把角度反过来,点取(-2,0)即可。
不知道是不是理解错了,题意写着两圆距离》2,《3.4,在求得时候就加了特判,一直WA。。。去了特判就过了。
为了提高精度,可以全化为atan2.
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
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 }