1. 程式人生 > >HDU 1272 小希的迷宮

HDU 1272 小希的迷宮

max 設計思路 ref 走了 ++ 提高 路徑 pri 分享

http://acm.hdu.edu.cn/showproblem.php?pid=1272

Problem Description 上次Gardon的迷宮城堡小希玩了很久(見Problem B),現在她也想設計一個迷宮讓Gardon來走。但是她設計迷宮的思路不一樣,首先她認為所有的通道都應該是雙向連通的,就是說如果有一個通道連通了房間A和B,那麽既可以通過它從房間A走到房間B,也可以通過它從房間B走到房間A,為了提高難度,小希希望任意兩個房間有且僅有一條路徑可以相通(除非走了回頭路)。小希現在把她的設計圖給你,讓你幫忙判斷她的設計圖是否符合她的設計思路。比如下面的例子,前兩個是符合條件的,但是最後一個卻有兩種方法從5到達8。
技術分享圖片
Input 輸入包含多組數據,每組數據是一個以0 0結尾的整數對列表,表示了一條通道連接的兩個房間的編號。房間的編號至少為1,且不超過100000。每兩組數據之間有一個空行。
整個文件以兩個-1結尾。 Output 對於輸入的每一組數據,輸出僅包括一行。如果該迷宮符合小希的思路,那麽輸出"Yes",否則輸出"No"。 Sample Input 6 8 5 3 5 2 6 4 5 6 0 0 8 1 7 3 6 2 8 9 7 5 7 4 7 8 7 6 0 0 3 8 6 8 6 4 5 3 5 6 5 2 0 0 -1 -1 Sample Output Yes Yes No 題解:並查集 代碼:
#include <bits/stdc++.h>
using namespace std;

const int maxn = 1e5 +10;
int f[maxn], A[maxn];
int N, M;
int cnt = 0;

void init() {
    for(int i = 1; i <= maxn; i ++)
        f[i] = i;
}

int Find(int x) {
    if(f[x] != x) f[x] = Find(f[x]);
    return f[x];
}

int Merge(int x, int y) {
    int fx = Find(x);
    int fy = Find(y);
    if(fx != fy) {
        f[fx] = fy;
        return 1;
    }
    else  return 0;
}

int main() {
    while(true) {
       init();
       int num = 0;
       bool flag = true;
       while(~scanf("%d%d", &N, &M)) {
            if(N == -1 && M == -1) return 0;
            else if(!N && !M) break;
            else if(flag) {
                if(!Merge(N, M)) flag = false;
                A[++ num] = N;
                A[++ num] = M;
            }
       }
        if(flag) {
                for(int j = 1; j <= num; j ++) {
                    if(Find(f[A[j]]) != Find(f[A[1]]))
                        flag = false;
                }
                if(flag) printf("Yes\n");
                else printf("No\n");
        }
        else printf("No\n");
    }
    return 0;
}

  

HDU 1272 小希的迷宮