高效算法设计专项:LA 2963
2013-06-02 12:31
309 查看
刚开始完全没思路,看了训练指南上的提示说是扫描法,然后往这方面想。仔细分析题目发现可以用O(n^2)的时间解决。不难发现可能的结果只可能是n个点两两距离的,然后可以从小到大扫描这n*(n-1)/2条边,然后维护当前符合条件的planet的个数。需要注意处理边长相等的情况。
#include <iostream> #include <cstdio> #include <algorithm> #include <cmath> using namespace std; #define M 1010 const double eps=1e-6; int dcmp(double x) { if(fabs(x)<eps) return 0; else return x<0?-1:1; } struct point { int x,y,z,p; } a[M]; struct edge { int u,v; double l; edge(int u=0,int v=0,double l=0):u(u),v(v),l(l){} bool operator<(const edge& tmp) const {return dcmp(l-tmp.l)<0;} } e[M*M]; double length(int i,int j) { int x=a[i].x-a[j].x,y=a[i].y-a[j].y,z=a[i].z-a[j].z; return sqrt(x*x+y*y+z*z); } int n,m; int c[M]; int main() { freopen("in.txt","r",stdin); while(scanf("%d",&n)!=EOF) { for(int i=0;i<n;i++) { scanf("%d%d%d%d",&a[i].x,&a[i].y,&a[i].z,&a[i].p); c[i]=1; } m=0; for(int i=0;i<n;i++) { for(int j=i+1;j<n;j++) { e[m++]=edge(i,j,length(i,j)); } } sort(e,e+m); int ans=0,cur=0; double len=0; for(int i=0;i<m;i++) { int u=e[i].u,v=e[i].v; double l=e[i].l; if(a[u].p!=a[v].p) { c[u]--; c[v]--; if(c[u]==-1) cur++; if(c[v]==-1) cur++; } else { c[u]++; c[v]++; if(c[u]==0) cur--; if(c[v]==0) cur--; } if(i!=m-1&&dcmp(l-e[i+1].l)==0) continue; if(cur>ans) { ans=cur; len=l; } } printf("%d\n",ans); printf("%.4f\n",len); } return 0; }
相关文章推荐
- 高效算法设计专项:LA 4726
- 高效算法设计专项:LA 4356
- 高效算法设计专项:LA 2689
- 高效算法设计专项:UVa 11572
- 高效算法设计专项:UVa 10125
- 高效算法设计专项:UVa 10810
- 高效算法设计专项:UVa 10827
- SEERC 2006 Subsequence, 高效算法设计 ,LA 2678
- 高效算法设计专项:UVa 10535
- 高效算法设计专项:UVa 10730
- 高效算法设计专项:UVa 11054
- 高效算法设计专项:UVa 10391
- 高效算法设计专项:UVa 10691
- A、B两个整数集合,设计一个算法求他们的交集,尽可能的高效。
- 集训第四周(高效算法设计)A题 Ultra-QuickSort
- 集训第四周(高效算法设计)C题 (二分查找优化题)
- 集训第四周(高效算法设计)I题 (贪心)
- 【高效算法设计——递归】 UVa 12627 Erratic Expansion
- 紫书_第八章_高效算法设计_8.3.1——棋盘覆盖问题
- 算法竞赛入门经典:第八章 高效算法设计 8.2归并排序