欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

求连通分量【图论】

程序员文章站 2022-03-25 14:50:11
...

求连通分量

Time Limit:1000MS Memory Limit:65536K
Total Submit:435 Accepted:258


Description
求一个图的连通分量


Input
n 顶点数(<=100)

Output
连通分量


Sample Input
8
6 3
1 2
2 5
5 4
4 1
8 7
0 0

Sample Output
4


解题思路

我们老师为了我们学会灵活运用,让我们整整打了五种方法!!!
┓(;´_`)┏ 心累
好吧,让我们进入正题,上图。。。
求连通分量【图论】
不知道连通分量l的请出门右转百度。。。

  • 深搜(邻接矩阵)
  • 深搜(邻接表)
  • 广搜 (邻接矩阵)
  • 广搜 (邻接表)
  • 广搜 (邻接表+STL)
    对于最后一种方法,
    用法如下:
    求连通分量【图论】

代码(五种)

求连通分量(深搜+邻接矩阵):


#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int n,a[1000][1000],v[1000],s,t[1000],ans=-1;
void dfs(int x){
	v[x]=1;
	for(int j=1;j<=n;j++)
	{
		if(a[x][j]&&!v[j])
		{
		  s++;
		  dfs(j);
		}
	}
}
int main(){
	scanf("%d",&n);
	int x,y;
	cin>>x>>y;
	while(x)
	{
		a[x][y]=1;
		a[y][x]=1;
		cin>>x>>y;
	}
	for(int i=1;i<=n;i++)
	{
		if(!v[i])
		{
		  s=1;
		  dfs(i);
		}
		ans=max(s,ans);
    }
	cout<<ans;
}

求连通分量 (深搜+邻接表)

#include<iostream>
#include<cstring>
#include<cstdio>
#include<cmath>
using namespace std;
int n,v[10000],s,k[10000],ans=-1,h,t,head[10000],kk;
struct{
	int x,next;
}a[1000]; 
void bfs(int x){
	v[x]=1;
	k[1]=x;
	h=0;
	t=1;
	do
	{
		h++;
		for(int i=head[k[h]];i;i=a[i].next)
		{
			if(!v[a[i].x])
			{	
			    t++;
				++s;
				v[a[i].x]=1;
				k[t]=a[i].x;
			}	
		}
	}while(h<t);
}
void add(int x,int y){
	++kk;
	a[kk].x=y;
	a[kk].next=head[x];
	head[x]=kk;
}
int main(){
	scanf("%d",&n);
	int x,y;
	cin>>x>>y;
	while(x)
	{
		add(x,y);
		add(y,x);
		cin>>x>>y;
	}
	for(int i=1;i<=n;i++)
	{
		if(!v[i])
		{
		  s=1;
		  bfs(i);
		}
		ans=max(s,ans);
    }
	printf("%d",ans);
}

求连通分量 (广搜+邻接矩阵)

#include<iostream>
#include<cstring>
#include<cstdio>
#include<cmath>
using namespace std;
int n,a[1000][1000],v[10000],s,k[10000],ans=-1,h,t;
void bfs(int x){
	v[x]=1;
	k[1]=x;
	h=0;
	t=1;
	do
	{
		h++;
		for(int i=1;i<=n;i++)
		{
			if(a[k[h]][i]&&!v[i])
			{	
			    t++;
				s++;
				v[i]=1;
				k[t]=i;
			}
			
		}
	}while(h<t);
}
int main(){
	scanf("%d",&n);
	int x,y;
	scanf("%d%d",&x,&y);
	while(x)
	{
		a[x][y]=1;
		a[y][x]=1;
		scanf("%d%d",&x,&y);
    }
    for(int i=1;i<=n;i++)
	{
		if(!v[i])
		{
		  s=1;
		  bfs(i);
		}
		ans=max(s,ans);
    }
	printf("%d",ans);
}

求连通分量 (广搜+邻接表)

#include<iostream>
#include<queue>
#include<cstring>
#include<cstdio>
#include<cmath>
using namespace std;
int n,v[10000],s,k[10000],ans=-1,h,t,head[10000],kk;
struct{
	int x,next;
}a[1000]; 
void bfs(int x){
	queue<int>k;
	v[x]=1;
	x=k.front();
	h=0;
	t=1;
	do
	{
		k.pop();
		for(int i=head[x];i;i=a[i].next)
		{
			if(!v[a[i].x])
			{	
				++s;
				v[a[i].x]=1;
		        k.push(a[i].x);
			}	
		}
	}while(k.size());
}
void add(int x,int y){
	++kk;
	a[kk].x=y;
	a[kk].next=head[x];
	head[x]=kk;
}
int main(){
	scanf("%d",&n);
	int x,y;
	cin>>x>>y;
	while(x)
	{
		add(x,y);
		add(y,x);
		cin>>x>>y;
	}
	for(int i=1;i<=n;i++)
	{
		if(!v[i])
		{
		  s=1;
		  bfs(i);
		}
		ans=max(s,ans);
    }
	printf("%d",ans);
}

求连通分量 (广搜+邻接表STL)

#include<iostream>
#include<queue>
#include<cstring>
#include<cstdio>
#include<cmath>
using namespace std;
int n,v[10000],s,k[10000],ans=-1,h,t,head[10000],kk;
struct{
	int x,next;
}a[1000]; 
void bfs(int x){
	int xx;
	queue<int>k;
	k.push(x);
	v[x]=1;
	h=0;
	t=1;
	do
	{
	    xx=k.front();
		k.pop();
		for(int i=head[xx];i;i=a[i].next)
		{
			if(!v[a[i].x])
			{	
				++s;
				v[a[i].x]=1;
		        k.push(a[i].x);
			}	
		}
	}while(k.size());
}
void add(int x,int y){
	++kk;
	a[kk].x=y;
	a[kk].next=head[x];
	head[x]=kk;
}
int main(){
	scanf("%d",&n);
	int x,y;
	cin>>x>>y;
	while(x)
	{
		add(x,y);
		add(y,x);
		cin>>x>>y;
	}
	for(int i=1;i<=n;i++)
	{
		if(!v[i])
		{
		  s=1;
		  bfs(i);
		}
		ans=max(s,ans);
    }
	printf("%d",ans);
}
相关标签: 图论