码迷,mamicode.com
首页 > 其他好文 > 详细

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

时间:2017-03-28 16:30:11      阅读:229      评论:0      收藏:0      [点我收藏+]

标签:题目   bool   scan   string   using   生成   print   char s   之间   

题目链接:http://poj.org/problem?id=3026

题意:题意就是从起点开始可以分成多组总权值就是各组经过的路程,每次到达一个‘A‘点可以继续分组,但是在路上不能分组

于是就是明显的最小生成树,点与点的距离要用bfs或者dfs求一下。这题bfs要稍微优化一下。不能下暴力的bfs就是两点两点之间

bfs这样会有很多重复的查询会超时,所以要一次性的bfs找到一个点就bfs到底。

 

#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <queue>
using namespace std;
int x , y , num , pos[200][200] , cost[200][200] , f[200] , dr[4][2] = {0 , 1 , 0 , -1 , 1 , 0 , -1 , 0};
char s[60][60] , cp[10];
void init() {
    for(int i = 0 ; i <= num ; i++) {
        f[i] = i;
    }
}
int find(int x) {
    if(x == f[x])
        return x;
    int tmp = find(f[x]);
    return f[x] = tmp;
}
struct TnT {
    int x , y , step;
};
struct node {
    int x , y , val;
}nodes[40000];
bool cmp(node a , node b) {
    return a.val < b.val;
}
bool vis[110][110] , have[110][110];
void bfs(int xx , int yy) {
    memset(vis , false , sizeof(vis));
    queue<TnT>q;
    vis[xx][yy] = true;
    TnT gg , gl;
    gg.x = xx , gg.y = yy , gg.step = 0;
    q.push(gg);
    while(!q.empty()) {
        gg = q.front();
        q.pop();
        if(pos[gg.x][gg.y] != -1) {
            cost[pos[xx][yy]][pos[gg.x][gg.y]] = gg.step;
        }
        for(int i = 0 ; i < 4 ; i++) {
            gl.x = gg.x + dr[i][0];
            gl.y = gg.y + dr[i][1];
            gl.step = gg.step + 1;
            if(gl.x >= 0 && gl.x < y && gl.y >= 0 && gl.y < x && s[gl.x][gl.y] != ‘#‘ && !vis[gl.x][gl.y]) {
                vis[gl.x][gl.y] = true;
                q.push(gl);
            }
        }
    }
}
int main() {
    int t;
    scanf("%d" , &t);
    while(t--) {
        scanf("%d%d" , &x , &y);
        gets(cp);
        for(int i = 0 ; i < y ; i++) {
            for(int j = 0 ; j < x ; j++) {
                pos[i][j] = -1;
                cost[i][j] = -1;
            }
        }
        num = 0;
        for(int i = 0 ; i < y ; i++) {
            gets(s[i]);
            for(int j = 0 ; j < x ; j++) {
                if(s[i][j] == ‘A‘ || s[i][j] == ‘S‘) {
                    pos[i][j] = num++;
                }
            }
        }
        for(int i = 0 ; i < y ; i++) {
            for(int j = 0 ; j < x ; j++) {
                if(s[i][j] == ‘A‘ || s[i][j] == ‘S‘) {
                    bfs(i , j);
                }
            }
        }
        init();
        int count = 0;
        for(int i = 0 ; i < num ; i++) {
            for(int j = i + 1 ; j < num ; j++) {
                if(cost[i][j] != -1) {
                    nodes[count].x = i , nodes[count].y = j , nodes[count].val = cost[i][j];
                    count++;
                }
            }
        }
        sort(nodes , nodes + count , cmp);
        int sum = 0 , temp = 0;
        for(int i = 0 ; i < count ; i++) {
            int a = find(nodes[i].x) , b = find(nodes[i].y);
            if(a != b) {
                f[a] = b;
                sum += nodes[i].val;
                temp++;
            }
            if(temp == num - 1)
                break;
        }
        printf("%d\n" , sum);
    }
    return 0;
}

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

标签:题目   bool   scan   string   using   生成   print   char s   之间   

原文地址:http://www.cnblogs.com/TnT2333333/p/6634821.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!