题目地址:点击打开链接
思路:建一个虚拟点,和所有的水库相连权值为自建水库的花费,跑一遍最小生成树就行,蓝桥杯题库的原题
AC代码:
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <stack>
#include <map>
#include <cstring>
#include <climits>
#include <cmath>
#include <cctype>
using namespace std;
const int zui = 1000000000;
int map1[310][310];
int cost[310];
int visit[310];
int lowdist[310];
int n;
void Prim()
{
memset(visit,0,sizeof(visit));
int i,j,k;
for(i=1; i<=n; i++)
{
lowdist[i] = map1[0][i];
}
visit[0] = 1;
int sum = 0;
for(i=1; i<=n; i++)//要并入n个点所以要循环n次
{
int min2 = zui;
for(j=1; j<=n; j++)
{
if(!visit[j] && lowdist[j] < min2)
{
min2 = lowdist[j];
k = j;
}
}
visit[k] = 1;
sum += lowdist[k];
for(j=1; j<=n; j++)
{
if(!visit[j] && map1[k][j] < lowdist[j])
{
lowdist[j] = map1[k][j];
}
}
}
printf("%d\n",sum);
}
int main()
{
int k;
int i,j;
scanf("%d",&k);
while(k--)
{
scanf("%d",&n);
int cost;
for(i=0; i<=n; i++)
{
for(j=0; j<=n; j++)
{
map1[i][j] = zui;
}
}
for(i=1; i<=n; i++)
{
scanf("%d",&cost);
map1[0][i] = map1[i][0] = cost;
//map1[0][i] = cost;
}
for(i=1; i<=n; i++)
{
for(j=1; j<=n; j++)
{
scanf("%d",&map1[i][j]);
}
}
Prim();
}
return 0;
}