zoukankan      html  css  js  c++  java
  • Luogu P1892 [BOI2003]团伙

    P1892 [BOI2003]团伙

    题目描述

    1920年的芝加哥,出现了一群强盗。如果两个强盗遇上了,那么他们要么是朋友,要么是敌人。而且有一点是肯定的,就是:

    我朋友的朋友是我的朋友;

    我敌人的敌人也是我的朋友。

    两个强盗是同一团伙的条件是当且仅当他们是朋友。现在给你一些关于强盗们的信息,问你最多有多少个强盗团伙。

    输入输出格式

    输入格式:

     

    输入文件gangs.in的第一行是一个整数N(2<=N<=1000),表示强盗的个数(从1编号到N)。 第二行M(1<=M<=5000),表示关于强盗的信息条数。 以下M行,每行可能是F p q或是E p q(1<=p q<=N),F表示p和q是朋友,E表示p和q是敌人。输入数据保证不会产生信息的矛盾。

     

    输出格式:

     

    输出文件gangs.out只有一行,表示最大可能的团伙数。

     

    输入输出样例

    输入样例#1:
    6
    4
    E 1 4
    F 3 5
    F 4 6
    E 1 2
    

      

    输出样例#1:
    3
    

      


     

     

    先说一下思路:

    对于只有朋友信息的数据就不用说了。对于敌人的信息,我们可以给每一个人i设置一个敌人集合E[i],当输入i和j时,我们就把i和E[j]合并,把j和E[i]合并。

    值得一提的是,要注意空集的处理,所谓空集就是一开始的时候,每个人都没有敌人。

     

    昨天晚上做了一晚上卡在了50分,今天又接着来啃,问同学,同学说我的想法很对,叫我自己慢慢调(WCNM我要是调的出来就不找你了)

    没办法,慢慢找喽。

    先给大家看看我的50分的代码。

     

    #include <iostream>
    #include <cstdio>
    
    using namespace std;
    
    int n, m, Ans, x, y;
    
    int f[1008], E[1008];
    
    char C;
    
    bool vis[1008];
    
    int find(int x) {
    	if(x == f[x]) return f[x];
    	else return f[x] = find(f[x]);
    }
    
    int main() {
    	scanf("%d%d", &n, &m);
    	for(int i=1; i<=n; i++) f[i] = i;
    	for(int i=1; i<=m; i++) {
    		cin>>C>>x>>y;
    		int xx, yy;	
    		if(C == 'E') {
    			if(E[x] != 0) {
    				f[y] = find(E[x]);
    			}
    			if(E[y] != 0) {
    				f[x] = find(E[y]);
    			}
    			E[x] = y, E[y] = x;
    		}
    		if(C == 'F') {
    			f[x] = find(y);
    		}
    	}
    	for(int i=1; i<=n; i++) {
    		if(!vis[find(i)]) {
    			vis[find(i)] = 1;
    			Ans++;
    		}
    	}
    	printf("%d", Ans);
    }
    

     

      

    不知道大家看出什么问题了没。

    没看出的同学可要小心了,

    看一下我的合并集合时候的操作,是不是把之前合并好的集合都打乱了。

    为什么?因为我合并时修改的是f[x]的值,而不是f[find(x)]的值,这就会导致很可怕的错误。

    往后的此类操作都是这样的。

    好了,说到这里该放上AC的代码了

    #include <iostream>
    #include <cstdio>
    
    using namespace std;
    
    int n, m, Ans, x, y;
    
    int f[1008], E[1008];
    
    char C;
    
    bool vis[1008];
    
    int find(int x) {
    	if(x == f[x]) return x;
    	else return f[x] = find(f[x]);
    }
    
    int main() {
    	scanf("%d%d", &n, &m);
    	for(int i=1; i<=n; i++) f[i] = i;
    	for(int i=1; i<=m; i++) {
    		cin>>C>>x>>y;
    		if(C == 'E') {
    			if(E[x] != 0) {	
    				f[find(y)] = find(E[x]);
    			}
    			else E[x] = find(y);
    			if(E[y] != 0) {
    				f[find(x)] = find(E[y]);
    			}
    			else E[y] = find(x);
    		}
    		if(C == 'F') {
    			f[find(x)] = find(y);
    		}
    	}
    	for(int i=1; i<=n; i++) {
    		if(!vis[find(i)]) {
    			vis[find(i)] = 1;
    			Ans++;
    		}
    	}
    	printf("%d", Ans);
    }
    

      

     

     

  • 相关阅读:
    牛客练习赛51 D题
    Educational Codeforces Round 72 (Rated for Div. 2) C题
    Codeforces Round #583 (Div. 1 + Div. 2, based on Olympiad of Metropolises) C题
    Codeforces Round #583 (Div. 1 + Div. 2, based on Olympiad of Metropolises) A题
    Codeforces Round #583 (Div. 1 + Div. 2, based on Olympiad of Metropolises) A题
    Educational Codeforces Round 72 (Rated for Div. 2) B题
    Educational Codeforces Round 72 (Rated for Div. 2) A题
    《DSP using MATLAB》Problem 7.2
    《DSP using MATLAB》Problem 7.1
    《DSP using MATLAB》Problem 6.24
  • 原文地址:https://www.cnblogs.com/bljfy/p/9085446.html
Copyright © 2011-2022 走看看