POJ - 2031 Building a Space Station(最小生成树)

题目传送门:POJ - 2031 Building a Space Station

题目大意:

给你n个球体,输入n,接下俩输入n行中每行有四个数,分别代表球的球心坐标x,y,z 和球径r 。

可以在两球之间建立通道,现在要将所有球体联通,求最小代价。

分析:

可以知道任意两个球都可以建立通道,因此我们构建一张图,里面是所有球的所有通道,然后在跑prim就可以了

通道的大小是(球心距-两个球的半径)  即   sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y)+(a.z-b.z)*(a.z-b.z))-a.r-b.r;(a,b表示两个球)

若该值小于等于0,则距离设置为0,因为他们重合或者相切可以直接到达距离为0。

代码:prim

#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<cmath>
using namespace std;
const int MAX=200;
const int INF=0x3f3f3f3f; 
int n;
double x,y,z,r;                    //记得这些都要double 
double map[MAX][MAX];
double dist[MAX];
bool vis[MAX];
struct point                    //结构体存储球的坐标和半径 
{
    double x,y,z,r;
    point(){}
    point(double a,double b,double c,double d)
    {
        x=a,y=b,z=c,r=d;
    }
}po[MAX];
double dis(point a,point b)        //计算两个球之间的距离 名字取distance会编译错误QAQ 
{double ans=sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y)+(a.z-b.z)*(a.z-b.z))-a.r-b.r;
    if(ans<=0)return 0;
    else return ans;
}
double prim()
{
    for(int i=0;i<n;i++)
    {
        dist[i]=INF;
        vis[i]=false;
    }
    dist[0]=0;
    double min,ans=0;
    int pos;
    for(int i=0;i<n;i++)
    {
        min=INF;
        for(int j=0;j<n;j++)
        {
            if(!vis[j]&&dist[j]<min)
            {
                min=dist[j];
                pos=j;
            }
        }
        vis[pos]=true;
        ans+=min;
        for(int j=0;j<n;j++)
        {
            if(!vis[j]&&dist[j]>map[pos][j])
                dist[j]=map[pos][j];
        }
    } 
    return ans;
}
int main()
{
    while(cin>>n&&n)
    {
        memset(po,0,sizeof(po));
        memset(map,0,sizeof(map));
        for(int i=0;i<n;i++)
        {    
            cin>>x>>y>>z>>r;    
            po[i]=point(x,y,z,r);
        }
        for(int i=0;i<n;i++)
            for(int j=i+1;j<n;j++)
                map[i][j]=map[j][i]=dis(po[i],po[j]);
            double ans=prim();
            printf("%.3lf\n",ans);
    }
    return 0;
}

 

posted @ 2018-08-17 11:00  _Carrot  阅读(231)  评论(0编辑  收藏  举报