2926问题 C: 团伙(group)

题目描述

在某城市里住着n个人,任何两个认识的人不是朋友就是敌人,而且满足:

1、我朋友的朋友是我的朋友;

2、我敌人的敌人是我的朋友;

所有是朋友的人组成一个团伙。告诉你关于这n个人的m条信息,即某两个人是朋友,或者某两个人是敌人,请你编写一个程序,计算出这个城市最多可能有多少个团伙?

输入

第1行为n和m,1<n<1000,1≤m≤100 000;

以下m行,每行为p x y,p的值为0或1,p为0时,表示x和y是朋友,p为1时,表示x和y是敌人。

输出

一个整数,表示这n个人最多可能有几个团伙。

 

样例输入

6 4

1 1 4

0 3 5

0 4 6

1 1 2

样例输出

3

思路

这是并查集的一种运用,首先我们先将所有父节点初始化为他们自己;

如果输入的两人是朋友,则进入并集函数,如果两人是敌人,则分别与对方的敌人并集,并记录各自的敌人数量;

最后遍历所有人,只要他的父节点是他自己便是根节点,而我们只需找到所有的根节点即为所有的团体数

代码:

#include<bits/stdc++.h>

using namespace std;

int tuan[100001],di[1001][1001];//tuan用来记录团伙,di[i][j]用来存储i的第j个敌人

int find(int x)//查集函数

{

       if(tuan[x]!=x)

       tuan[x]=find(tuan[x]);

       return tuan[x];

}

void unionn(int r1,int r2)

{

       tuan[r2]=r1;//团伙的并集

}

int main()

{

       int n,m;

       cin>>n>>m;

       for(int i=1;i<=n;i++)

       tuan[i]=i;//先将所有父节点定为他们自己

       for(int i=1;i<=m;i++)

       {

              int p,x,y;

              cin>>p>>x>>y;

              if(p==0)//p==0时他们是朋友,所以并集

              {

                     if(find(x)!=find(y))

                     unionn(find(x),find(y));

              }

              Else//p==1时他们是敌人,将敌人的敌人并集

              {

                     for(int j=1;j<=di[x][0];j++)

                     {

                            if(find(y)!=find(di[x][j]))

                            unionn(find(y),find(di[x][j]));

                     }     

                     for(int j=1;j<=di[y][0];j++)

                     {

                            if(find(x)!=find(di[y][j]))

                            unionn(find(x),find(di[y][j]));

                     }

                     di[y][0]++;//记录敌人的个数

                     di[y][di[y][0]]=x;

                     di[x][0]++;

                     di[x][di[x][0]]=y;

                    

              }

        }

        int a=0;//要找到集合的个数,只需找到根节点的个数,a用来记录根节点的个数

       for(int i=1;i<=n;i++)

       if(tuan[i]==i) //当父节点就是自己本身时,就是那个集合的根节点

       a++;

       cout<<a<<endl;

}

 

全部评论

相关推荐

02-12 20:22
重庆大学 Java
字节暑期刚入职四天,因为是年前,所以很多正职都放假走了,也就没有给我分配mt,然后有一个老哥在我来的时候给我发了一个landing手册,然后还有关于部门业务的白皮书,还有一些业务代码。然后本人是java面的,进来第一次接触go语言&nbsp;前面几天熟悉了一下go的语法和go的框架,可以读但是还不太会写,然后业务白皮书也看的很头疼,包括landing手册里要了解的很多东西说实话我看文档真的快看死了,一个嵌套一个,问题是我还完全不知道咋用这个我了解的东西,还有就是那个项目代码,那个老哥喊我去写写单测,熟悉一下go的语法,但也进行的很困难(这是我第一段实习,之前都是springboot那一套,真不太熟悉这个)想问问大家的建议,就是我从现在开始到在开年回来之前应该做些什么,我目前就一个想法&nbsp;就是复现一个landing手册上的go框架小项目&nbsp;就是相当于帮自己锻炼锻炼怎么写go&nbsp;或者各位大佬有没有更好的锻炼go语法的建议还有就是大家都在说vibe&nbsp;coding,那我应该怎么锻炼自己使用ai的能力,感觉我除了给一些需求然后它给我生成代码,好像就没别的用法了,那些什么工作流、拆解、skill啥的都不知道从哪一个地方开始,包括我现在正在实习,不知道精力该怎么分配,去网上想找找关于agent开发的一些学习流程,说实话,众说纷纭,有的是从python开始打基础然后系统学那些rag&nbsp;prompt&nbsp;langchain&nbsp;mcp等等,有的是说直接找一个github上的ai项目然后反复问ai,我确实有点迷茫,恳求各位大佬能留下你们宝贵的建议,我一定认真反复深刻学习有一说一&nbsp;我觉得字节饭挺好吃的!
Jasonnnnnn...:直接把项目代码喂给AI然后让它帮你分析,如果组里已经有一些流程图总结的话最好,没有的话自己画一个 Go的话其实只要把基础语法搞明白就行了,项目里很多都是直接让ai帮你写好然后自己稍微改下,不用学的特别深 ai的话,可以自己写一些md文件来搞点小东西,但除非你打算转算法,否则不用把rag langchain学的特别深,了解下就行了
字节跳动公司福利 1371人发布
点赞 评论 收藏
分享
2025-12-26 10:52
河北传媒学院 Java
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务