某地区经过对城镇交通状况的调查,得到现有城镇间快速道路的统计数据,并提出“畅通工程”的目标:使整个地区任何两个城镇间都可以实现快速交通(但不一定有直接的快速道路相连,只要互相间接通过快速路可达即可)。现得到城镇道路统计表,表中列出了任意两城镇间修建快速路的费用,以及该道路是否已经修通的状态。现请你编写程序,计算出全地区畅通需要的最低成本。
输入格式:
输入的第一行给出村庄数目N (1≤N≤100);随后的N(N−1)/2行对应村庄间道路的成本及修建状态:每行给出4个正整数,分别是两个村庄的编号(从1编号到N),此两村庄间道路的成本,以及修建状态 — 1表示已建,0表示未建。
输出格式:
输出全省畅通需要的最低成本。
输入样例:
4
1 2 1 1
1 3 4 0
1 4 1 1
2 3 3 0
2 4 2 1
3 4 5 0
输出样例:
3
代码:
#include<stdio.h>
#include<stdlib.h>
#define MAX 101
#define INFINITY 65535
bool is_mark[MAX];//标记是否合并
int pathmatrirx[MAX][MAX];//所有路径长
int Dist[MAX];//当前连通量与其他地点的最短距离
int main()
{
int numofvertex;
scanf("%d",&numofvertex);
for(int i = 0; i < numofvertex; i++) {
for(int j = 0; j < numofvertex; j++)
pathmatrirx[i][j] = INFINITY;//初始化路径为最长
}
int arcs = numofvertex*(numofvertex-1)/2;
//输入边即道路修建成本
for(int i = 0; i < arcs; i++) {
int vil1,vil2,cost,state;
scanf("%d%d%d%d",&vil1,&vil2,&cost,&state);
//如果该道路已修好,则不计成本
if(state == 1) {
pathmatrirx[vil1-1][vil2-1] = pathmatrirx[vil2-1][vil1-1] = 0;
}
//否则,记录修建成本
else {
pathmatrirx[vil1-1][vil2-1] = pathmatrirx[vil2-1][vil1-1] = cost;
}
}
//初始化Dist表
for(int i = 0; i < numofvertex; i++) {
Dist[i] = pathmatrirx[0][i];
}
//标记第一个点,且第一个点到自身的距离更改为0
is_mark[0] = 0;
Dist[0] = 0;
int sum = 0;
for(int i = 0; i < numofvertex; i++) {
int minpath = INFINITY;
int order = -1;
for(int j = 1; j < numofvertex; j++) {
if(minpath > Dist[j] && !is_mark[j]) {
minpath = Dist[j];//选取目前离连通量最小的路径
order = j;//记录离目前连通量最近的点的坐标
}
}
//合并该点(标记该点)
is_mark[order] = true;
//每合并一个点,修改其他点到目前连通量的最小路径
if(order != -1) {
//最小路径求和
sum += minpath;
for(int j = 1; j < numofvertex; j++) {
if(Dist[j] > pathmatrirx[order][j] && !is_mark[j]) {
//如果有点距离当前连通量的距离小于原距离,修改Dist表
Dist[j] = pathmatrirx[order][j];
}
}
}
}
printf("%d\n",sum);
return 0;
}