POJ 1703 Find them, Catch them
题意:
有两个帮派龙帮,蛇帮,警察须要验证嫌疑人属于哪个帮派。须要解决的问题是,给出两个嫌疑人,你必须通过不全然的信息,推断他们是否属于一样帮派。
有 N ( 1 < N < 100000 ) 个嫌疑人,标号 1 到 N,至少有一个属于龙帮,一个属于蛇帮。有 M ( 1 < M < 100000 ) 条信息,有两种类型的信息,
1.D a b 意味着 a 和 b 属于不同帮派
2.A a b 查询 a 和 b 是否属于一个帮派
输入:
第一行測试次数,第二行两个整数,N,M 意味着有 N 个嫌疑人和 M 条信息
接下来的M行输入信息
输出:
对于每一个 A a b 的输出,有三种可能,“不能确定”,“不在一个帮派”,“在一个帮派”,输出一种。
比方输入:
1
5 5
A 1 2
D 1 2
A 1 2
D 2 4
A 1 4
比方输出:
Not sure yet.
In different gangs.
In the same gang.
思路:
并查集,代码非常清楚。
#include <iostream> #include <cstdio> #include <string.h> using namespace std; #define MAX_SIZE 100010 #define UNKOWN -1 int others[MAX_SIZE]; // 非该嫌疑人本人的帮派(干脆叫该嫌疑人的敌对帮派吧) int parents[MAX_SIZE]; int find_gang( int suspect ){ if( suspect != parents[suspect] ) parents[suspect] = find_gang( parents[suspect] ); return parents[suspect]; } // 简单的合并了下 void merge_gang( int suspect_a, int suspect_b ){ int gang_of_a = find_gang( suspect_a ); int gang_of_b = find_gang( suspect_b ); parents[gang_of_a] = gang_of_b; } // 将两个嫌疑人分配到不同的帮派里面 void differ( int suspect_a, int suspect_b ){ // 若是 a 的敌对帮派未知,那么僵敌对帮派设为 b if( others[suspect_a] == UNKOWN ){ others[suspect_a] = suspect_b; } else{ // a 的敌对帮派已知,那么就将 b 与 a 的敌对帮派归为一类 merge_gang( others[suspect_a], suspect_b ); } // 若是 b 的敌对帮派未知,那么僵敌对帮派设为 a if( others[suspect_b] == UNKOWN ){ others[suspect_b] = suspect_a; } else{ // b 的敌对帮派已知,那么就将 a 与 b 的敌对帮派归为一类 merge_gang( others[suspect_b], suspect_a ); } } void answer( int suspect_a, int suspect_b ){ if( others[suspect_a] == UNKOWN || others[suspect_b] == UNKOWN ){ cout << "Not sure yet.\n"; return; } int gang_of_a = find_gang( suspect_a ); int gang_of_b = find_gang( suspect_b ); int other_gang_of_a = find_gang( others[suspect_a] ); int other_gang_of_b = find_gang( others[suspect_b] ); if( gang_of_a == gang_of_b ){ cout << "In the same gang.\n"; return; } // 若是 a 的帮派和 b 的敌对帮派一致,证明 a,b 不在一个帮派 if( gang_of_a == other_gang_of_b ){ cout << "In different gangs.\n"; return; } cout << "Not sure yet.\n"; } int main(){ int test_num; scanf( "%d", &test_num ); while( test_num-- ){ memset( others, UNKOWN, sizeof( others ) ); int suspect_num, msg_num; scanf( "%d%d", &suspect_num, &msg_num ); for( int i = 0; i <= suspect_num; ++i ) parents[i] = i; while( msg_num-- ){ char ch; int suspect_a; int suspect_b; scanf("\n%c%d%d", &ch, &suspect_a, &suspect_b); if( ch == 'D' ){ differ( suspect_a, suspect_b ); } else{ answer( suspect_a, suspect_b ); } } } return 0; }