zoukankan      html  css  js  c++  java
  • 1007 Quoit Design (杭电)

    Quoit Design

    Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)
    Total Submission(s): 22320    Accepted Submission(s): 5729


    Problem Description
    Have you ever played quoit in a playground? Quoit is a game in which flat rings are pitched at some toys, with all the toys encircled awarded.
    In the field of Cyberground, the position of each toy is fixed, and the ring is carefully designed so it can only encircle one toy at a time. On the other hand, to make the game look more attractive, the ring is designed to have the largest radius. Given a configuration of the field, you are supposed to find the radius of such a ring.

    Assume that all the toys are points on a plane. A point is encircled by the ring if the distance between the point and the center of the ring is strictly less than the radius of the ring. If two toys are placed at the same point, the radius of the ring is considered to be 0.
     
    Input
    The input consists of several test cases. For each case, the first line contains an integer N (2 <= N <= 100,000), the total number of toys in the field. Then N lines follow, each contains a pair of (x, y) which are the coordinates of a toy. The input is terminated by N = 0.
     
    Output
    For each test case, print in one line the radius of the ring required by the Cyberground manager, accurate up to 2 decimal places. 
     
    Sample Input
    2
    0 0
    1 1
    2
    1 1
    1 1
    3
    -1.5 0
    0 0
    0 1.5
    0
     
    Sample Output
    0.71
    0.00
    0.75
     ----------------------------------------------------------------------------------------------------------------------------------------
    此题使用Divide and Conquer的方法,首先将根据点的X(或Y)的值进行排序,将排序后的数组从中间分隔成两部分,计算每部分的最小值,由于距离最近的点对(即两个点)有可能一个出现在左段部分,另一个出现在右段部分,而且可以确定这两个点距离中间点(即将数组分成两部分的那个点)的距离都小于每部分的最小值。根据此条件,将可疑范围内的点都复制到一个新数组里面,此时X(或者Y)轴的值差距不是太大,而且也有可能含有很多点,此时根据Y(或者X)对新数组进行排序,遍历排序后的新数组,对每一个点,与这点Y(或者X)的距离小于最小值的点,计算此两点间的距离,与最小距离比较,更新最小距离。
     1 #include <cstdlib>
     2 #include <cstdio>
     3 #include <cfloat>
     4 #include <cmath>
     5 
     6 typedef struct{
     7     double x;
     8     double y;
     9 } point;
    10 
    11 const int magic=100000+10;
    12 point array[magic],arrayX[magic];
    13 
    14 int compareX(const void * a,const void * b){
    15     double tmp;
    16      if(((point*)a)->x==((point*)b)->x)
    17         tmp=((point*)a)->y-((point*)b)->y;
    18     else 
    19         tmp=((point*)a)->x-((point*)b)->x;
    20     return (tmp>0?1:-1);
    21 }
    22 
    23 int compareY(const void * a,const void * b){
    24     double tmp;
    25     if(((point*)a)->y==((point*)b)->y)
    26         tmp=((point*)a)->x-((point*)b)->x;
    27     else
    28         tmp=((point*)a)->y-((point*)b)->y;
    29     return (tmp>0?1:-1);
    30 }
    31 
    32 double distance(point a,point b){
    33     double x=a.x-b.x,y=a.y-b.y;
    34     return sqrt(x*x+y*y);
    35 }
    36 
    37 double getMinDistance(point array[],int start,int end){
    38     double radius,tmp;
    39     if(end<=start+1)
    40         return DBL_MAX;
    41     if(end-start==2)
    42         return distance(array[start],array[start+1]);
    43     if(end-start==3){
    44         radius=distance(array[start],array[start+1]);
    45         tmp=distance(array[start],array[start+2]);
    46         radius=(radius>tmp?tmp:radius);
    47         tmp=distance(array[start+1],array[start+2]);
    48         radius=(radius>tmp?tmp:radius);
    49         return radius;
    50     }
    51 
    52     int mid=start+((end-start)>>1);
    53     double left=getMinDistance(array,start,mid);
    54     double right=getMinDistance(array,mid,end);
    55     radius=(left<right?left:right);
    56 
    57     int index=0;
    58     for(int i=mid-1;i>=start&&array[mid].y-array[i].y<radius;i--)
    59         arrayX[index++]=array[i];
    60     for(int i=mid;i<end&&array[i].y-array[mid].y<radius;i++)
    61         arrayX[index++]=array[i];
    62     
    63     qsort(arrayX,index,sizeof(point),compareX);
    64 
    65     for(int i=0;i<index;i++)
    66         for(int j=i+1;j<index;j++){
    67             if (arrayX[j].x-arrayX[i].x>radius)
    68                 break;
    69             tmp=distance(arrayX[i],arrayX[j]);
    70             if(tmp<radius)
    71                 radius=tmp;
    72         }
    73     return radius;
    74 }
    75 
    76 int main(){
    77     int n;
    78     while(scanf("%d",&n)&&n>0){
    79         for(int i=0;i<n;i++)
    80             scanf("%lf%lf",&(array[i].x),&(array[i].y));    
    81         qsort(array,n,sizeof(point),compareY);
    82         printf("%.2f
    ",getMinDistance(array,0,n)/2);
    83     }
    84     return 0;
    85 }
  • 相关阅读:
    《NoSQL精粹》读书笔记
    react+flux编程实践(一) 基础篇
    MongoDB索引(一) --- 入门篇:学习使用MongoDB数据库索引
    (译+注解)node.js的C++扩展入门
    深入解析Javascript异步编程
    (译)package.json详解
    Protobuf学习
    Redis学习
    MySQL学习-常用命令整理
    TCP/IP-TCP
  • 原文地址:https://www.cnblogs.com/purgiant/p/3199911.html
Copyright © 2011-2022 走看看