poj 2187 Beauty Contest(旋转卡壳求最远点对)

资料:

 

http://www.cnblogs.com/Booble/archive/2011/04/03/2004865.html

 

http://www.cnblogs.com/DreamUp/archive/2010/09/16/1828131.html

 

旋转卡壳的思想挺好理解的。

 

但是里面有点东西需要注意:

 

所求的凸包必须是纯净的(即凸包上的点没有三点共线的),不过第二个网址给了旋转卡壳处理不纯净凸包的方法。

 

我写了个纯净的凸包,那么旋转卡壳里的求最大值可以变成ans = max(ans,Dis(c[stk[i]],c[stk[q]]));这个啦~

 

完全不纯净的凸包。。。GB说他和大黄都木有做出来T T 。。

 

#include <stdlib.h>#include <iostream>#include <algorithm>#include <math.h>using namespace std;const int MAX = 50010;const double eps = 1e-6;typedef struct Point{double x,y;}Point;Point c[MAX];bool dy(double x,double y) { return x > y + eps;} // x > y bool xy(double x,double y) { return x < y - eps;} // x < y bool dyd(double x,double y) { return x > y - eps;} // x >= y bool xyd(double x,double y) { return x < y + eps;} // x <= y bool dd(double x,double y) { return fabs( x - y ) < eps;} // x == ydouble crossProduct(Point a,Point b,Point c)//向量 ac 在 ab 的方向 {return (c.x - a.x)*(b.y - a.y) - (b.x - a.x)*(c.y - a.y);}double disp2p(Point a,Point b) // a b 两点之间的距离 {return sqrt( ( a.x - b.x ) * ( a.x - b.x ) + ( a.y - b.y ) * ( a.y - b.y ) );}double Dis(Point a,Point b) {return ( ( a.x - b.x ) * ( a.x - b.x ) + ( a.y - b.y ) * ( a.y - b.y ) );}bool cmp(Point a,Point b){double len = crossProduct(c[0],a,b);if( dd(len,0.0) )return xy(disp2p(c[0],a),disp2p(c[0],b));return xy(len,0.0);}double max(double x,double y){return dy(x,y)?x:y;}int stk[MAX];int top;double Rotating_calipers(int stk[],int n){stk[n] = stk[0];int q = 1;double ans = 0.0;for(int i=0; i<n; i++){while( xy(fabs(crossProduct(c[stk[i]],c[stk[i+1]],c[stk[q]])),fabs(crossProduct(c[stk[i]],c[stk[i+1]],c[stk[q+1]]))) )q = (q+1)%n;ans = max(ans,Dis(c[stk[i]],c[stk[q]]));}return ans;}double Graham(int n){ int tmp = 0; for(int i=1; i<n; i++) if( xy(c[i].x,c[tmp].x) || dd(c[i].x,c[tmp].x) && xy(c[i].y,c[tmp].y) ) tmp = i; swap(c[0],c[tmp]); sort(c+1,c+n,cmp); stk[0] = 0; stk[1] = 1; top = 1;for(int i=2; i<n; i++){while( xyd( crossProduct(c[stk[top]],c[stk[top-1]],c[i]), 0.0 ) && top >= 1 )top--;stk[++top] = i;}return Rotating_calipers(stk,top+1);}int main(){int n;while( ~scanf("%d",&n) && n ){for(int i=0; i<n; i++)scanf("%lf %lf",&c[i].x,&c[i].y);int ans = (int)Graham(n);printf("%d/n",ans);}return 0;} 

 

 

 

你可能感兴趣的:(c,struct,2010)