hdu3585 maximum shortest distance

maximum shortest distance


Problem Description
There are n points in the plane. Your task is to pick k points (k>=2), and make the closest points in these k points as far as possible.
 

Input
For each case, the first line contains two integers n and k. The following n lines represent n points. Each contains two integers x and y. 2<=n<=50, 2<=k<=n, 0<=x,y<10000.
 

Output
For each case, output a line contains a real number with precision up to two decimal places.

 

Sample Input
   
   
   
   
3 2 0 0 10 0 0 20
 

Sample Output
   
   
   
   
22.36
 

Author
alpc50
 

Source
2010 ACM-ICPC Multi-University Training Contest(15)——Host by NUDT

题意: 在N个点钟 选出K个点 使得这K个点间的最小距离最大
思路:二分答案+最大团
#include<bits/stdc++.h>
using namespace std;
#define Hash(a,b) (a-1)*n+b
const int maxn=51;
double mp[maxn][maxn];
int num[maxn],k;
int G[maxn][maxn],ret;

bool dfs(int *adj,int tot,int cnt){
    if(cnt>=k){
        ret=cnt;
        return 1;
    }
    if(tot==0){
        if(cnt>ret){
            ret=cnt;
            return 1;
        }
        return 0;
    }
    for(int i=0;i<tot;i++){
        if(cnt+tot-i<=ret)
            continue;
        if(cnt+num[adj[i]]<=ret)
            continue;
        int t[maxn],k=0;
        for(int j=i+1;j<tot;j++){
            if(G[adj[i]][adj[j]])
                t[k ++] = adj[j];
        }
        if(dfs(t,k,cnt+1))
            return 1;
    }
    return 0;
}

void Maxclique(int n){
    int adj[maxn],tot;
    for(int i=n;i>=1;i--){
        tot=0;
        for(int j=i+1;j<=n;j++)
            if(G[i][j]==1)
                adj[tot++]=j;
        dfs(adj,tot,1);
        if(ret>=k)
            return ;
        num[i]=ret;
    }
}

struct Point{
    double x,y;
}node[maxn];

double distance(int i,int j){
    return sqrt((node[i].y-node[j].y)*(node[i].y-node[j].y)+(node[i].x-node[j].x)*(node[i].x-node[j].x));
}

int main(){
    int _;
    int n;
    while(scanf("%d%d",&n,&k)!=EOF){
        memset(G,0,sizeof(G));
        ret=0;
        for(int i=1;i<=n;i++)
            scanf("%lf%lf",&node[i].x,&node[i].y);
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                mp[i][j]=distance(i,j);
        double low=0,high=20000;
        while(high-low>=1e-4){
            ret=0;
            double mid=(low+high)/2;
            for(int i=1;i<=n;i++)
                for(int j=1;j<=n;j++){
                    if(mp[i][j]>=mid)
                        G[i][j]=1;
                    else
                        G[i][j]=0;
                }
            Maxclique(n);
            if(ret>=k)
                low=mid+(1e-4);
            else
                high=mid-(1e-4);
        }
        printf("%.2f\n",(high+low)/2);
    }
    return 0;
}


 

你可能感兴趣的:(hdu3585 maximum shortest distance)