uva 11168 Airport
https://vjudge.net/problem/UVA-11168
给出n个点,求一条直线,使所有点在直线的同侧,且平均距离最小
输出最小的平均距离
直线一定是凸包的一条边
求出凸包每一条边一般式Ax+By+C
所有点到这条边的距离和=abs(A*sumx+B*sumy+C*n)/sqrt(A^2+B^2)
#include<cmath> #include<cstdio> #include<iostream> #include<algorithm> using namespace std; #define N 10001 typedef long long LL; const double eps=1e-10; struct Point { int x,y; Point (int x_=0,int y_=0) : x(x_),y(y_) { } }; typedef Point Vector; Point P[N],ch[N]; Vector operator - (Vector A,Vector B) { return Vector(A.x-B.x,A.y-B.y); } void read(int &x) { x=0; int f=1; char c=getchar(); while(!isdigit(c)) { if(c=='-') f=-1; c=getchar(); } while(isdigit(c)) { x=x*10+c-'0'; c=getchar(); } x*=f; } int dcmp(int x,int y) { if(abs(x-y)<eps) return 0; return x<y ? -1 : 1; } bool cmp(Point A,Point B) { if(!dcmp(A.x,B.x)) return A.y<B.y; return A.x<B.x; } LL Cross(Vector A,Vector B) { return (LL)A.x*B.y-(LL)A.y*B.x; } int ConvexHull(Point *p,int n,Point *c) { sort(p,p+n,cmp); int m=0; for(int i=0;i<n;++i) { while(m>1 && Cross(c[m-1]-c[m-2],p[i]-c[m-2])<=0) m--; c[m++]=p[i]; } int k=m; for(int i=n-2;i>=0;--i) { while(m>k && Cross(c[m-1]-c[m-2],p[i]-c[m-2])<=0) m--; c[m++]=p[i]; } if(n>1) m--; return m; } double solve(int n,int m) { int sx=0,sy=0; for(int i=0;i<n;++i) { sx+=P[i].x; sy+=P[i].y; } double A,B,C; double ans=2e9; for(int i=0;i<m;++i) { if(!dcmp(ch[i].x,ch[i+1].x)) { A=1; B=0; C=ch[i].x; } else { A=1.0*(ch[i].y-ch[i+1].y)/(ch[i].x-ch[i+1].x); B=-1; C=ch[i].y-ch[i].x*A; } ans=min(ans,fabs(A*sx+B*sy+C*n)/sqrt(A*A+B*B)); } return ans/n; } int main() { int T,n,x,y; read(T); for(int t=1;t<=T;++t) { read(n); for(int i=0;i<n;++i) { read(x); read(y); P[i]=Point(x,y); } if(n<=2) { printf("Case #%d: 0.000\n",t); continue; } int m=ConvexHull(P,n,ch); printf("Case #%d: %.3lf\n",t,solve(n,m)); } }