您的位置:首页 > 其它

Borg Maze poj 3026(bfs+最小生成树)

2015-09-24 19:23 351 查看
题目链接: http://poj.org/problem?id=3026
题意:一对警察(S)抓捕外星人(A),‘#’代表墙,‘_’(空格)代表可以通过的路,从S处出发,问最少走多长的路可以把外星人全部KO了!注意:当他们在S处或是当抓捕到某个外星人以后,可以分开成几个队伍向周围继续抓捕,总的路程等于每支队伍的总和!

#include <cstdio>
#include <cstring>
#include <queue>
#include <iostream>
#define N 130
#define INF 0x3f3f3f3f
using namespace std;
int n, k;
bool vis[N*N];
int dis

, lostcow[N*N];
int map

, cost

;
char str

;
int dx[] = {0, 0, 1, -1}, dy[] = {1, -1, 0, 0};
void bfs(int x, int y)
{
int tx, ty, i, ttx, tty;
queue<pair<int, int> >Q;
memset(dis, 0, sizeof(dis));
Q.push(make_pair(x, y));
dis[x][y] = 0;
while(!Q.empty())
{
tx = Q.front().first, ty = Q.front().second;
Q.pop();
if(map[tx][ty])
cost[map[x][y]][map[tx][ty]] = dis[tx][ty];/*   cost用于存字母和字母间的权值    */
for(i = 0; i < 4; i++)
{
ttx = tx + dx[i], tty = ty + dy[i];
if(ttx >= 0 && ttx < k && tty >= 0 && tty < n)
{
if(str[ttx][tty] == '#' || dis[ttx][tty])
continue;
dis[ttx][tty] = dis[tx][ty] + 1;
Q.push(make_pair(ttx, tty));
}
}
}
}
int prim(int nn)
{
int sum = 0, i, j, m;
memset(vis, 0, sizeof(vis));
for(i = 1; i <= nn; i++)
lostcow[i] = cost[1][i];
vis[1] = 1;
for(i = 1; i < nn; i++)
{
m = 1;
int min = INF;
for(j = 1; j <= nn; j++)
if(!vis[j] && lostcow[j] < min)
{
min = lostcow[j];
m = j;
}
vis[m] = 1;
if(min != INF)
sum += min;
for(j = 1; j <= nn; j++)
if(!vis[j] && lostcow[j] > cost[m][j])
lostcow[j] = cost[m][j];
}
return sum;
}
int main()
{
int t, i, j;
scanf("%d", &t);
while(t--)
{
int num = 1;
memset(map, 0, sizeof(map));
memset(cost, 0, sizeof(cost));
scanf("%d%d", &n, &k);
gets(str[0]);/*     用getchar()不行    */
for(i = 1; i <= k; i++)
{
gets(str[i]);
for(j = 1; j <= n; j++)
if(str[i][j] == 'A' || str[i][j] == 'S')/*      字母和字母之间建最小生成树     */
map[i][j] = num++;
}
for(i = 1; i <= k; i++)
for(j = 1; j <= n; j++)
if(map[i][j])
bfs(i, j);/*    求每个字母之间的权值      */
printf("%d\n", prim(num-1));
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: