Kruskal算法变形 poj2349

本文介绍了一种使用Kruskal算法变形来寻找具有特定卫星通信限制的最短树的方法。通过初始化每个节点并进行并查集操作,逐步合并不同树以构建最短树,并计算出满足条件的最短距离。程序中还包含了二维坐标点间的距离计算以及边的排序策略,以确保找到最优解。
摘要由CSDN通过智能技术生成
在这里插入代码片
```#include<cstdio>
#include<cstdlib>
#include<iostream>
#include<cmath>
#include<queue>
#include<algorithm>
using namespace std;
typedef struct ENode{
	int start;
	int end;
	double weight;	
}ENode;
ENode E[250005];
int p[505];  //结点的前驱 
int x[505],y[505];  //记录点的坐标的数组 
double len[250005];  //记录组成最短树的路的长度
int q;
void Init(int n){   //初始化,每个结点都单独成树 
	for(int i=1;i<=n;i++) 
		p[i]=i;
}
int Find(int i){         //找根节点 
	if(p[i]==i)
		return i;
	else
		return p[i]=Find(p[i]);//将该路径上的结点的前驱结点都改为根节点 
}
int Union(int a,int b){   //将ab在的树合为一棵树 
	if(Find(a)==Find(b))
		return 0;
	else{
		p[Find(b)]=Find(a);  //b的根节点的前驱改为a的根节点 
		return 0;
	}		
}
void Kruskal(int n,int m){// n是结点个数,m是边的总数 
	q=0;  //作为边的下标 
	Init(n);  
	for(int i=1;i<=m;i++){
		int a=Find(E[i].start);
		int b=Find(E[i].end);
		if(a!=b){
			Union(a,b);
			len[++q]=E[i].weight;
		}
	}
}
double dist(int a,int b){
	return sqrt((double)(x[a]-x[b])*(x[a]-x[b])+(y[a]-y[b])*(y[a]-y[b]));
}
bool cmp(ENode a,ENode b){
	return a.weight<b.weight;
}
int main(){
	int N;
	cin>>N;
	while(N--){
		int S,P;
		cin>>S>>P; 
		int cnt=0;
		for(int i=1;i<=P;i++){
			cin>>x[i]>>y[i];
		}
		for(int i=1;i<=P;i++)
			for(int j=i+1;j<=P;j++){
				E[++cnt].weight=dist(i,j);
				E[cnt].start=i;
				E[cnt].end=j;
			}
		sort(E+1,E+1+cnt,cmp);
		q=0;
		Kruskal(P,cnt);
		int to=q-S+1;   //有S-1个地方是可以用卫星通信的 
			printf("%.2f\n", len[to]);
	}
	return 0;
}

## 标题POJ2349 Kruskal算法的变形
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值