看了并查集的视频,讲的挺清楚的: https://www.bilibili.com/video/BV13t411v7Fs?p=2
然后就分模块写了代码:
创建一维数组并初始化
#define MAX_TREE_SIZE 10010
int parent[MAX_TREE_SIZE]={0};//创建一个结点数组
void initial(int n)//初始化
{
for(int i=0;i<n;i++)
{
parent[i]=-1;
}
}
寻找根节点
int find_root(int x)//寻找根结点
{
int x_root=x;
while(parent[x_root]!=-1)// parent[x_root]!=-1说明不是根节点,就一层一层往上找
{
x_root=parent[x_root];
}
return x_root;
}
合并所在集合
void combine(int x,int y)//合并集合
{
int x_root=find_root(x);
int y_root=find_root(y);
if(x_root!=y_root)
parent[x_root]=y_root;
}
检查是否在同一集合
void check(int x,int y)//检查x,y是否在同一集合 ,只要检查他们根节点是不是同一个就好了
{
int x_root=find_root(x);
int y_root=find_root(y);
if(x_root==y_root)//如果x,y的根节点相同,说明他们在同一集合
cout<<"Y"<<endl;
else
cout<<"N"<<endl;
}
主函数内输入
int main()
{
int n,m;
cin>>n>>m;//输入,N个元素和 M个操作
initial(n);
int z,x,y;
for(int i=0;i<m;i++)
{
cin>>z>>x>>y;//输入三个整数,进行后续操作
if(z==1)
{
combine(x,y);//将x,y所在集合合并
}
else if(z==2)
{
check(x,y);//输出x,y是否在同一集合
}
else
{
cout<<"输入错误";
exit(0);
}
}
}
结果没问题
三个测试点TLE,时间超限,应该是减掉了视频里第三个步骤导致的
再创建一个rank数组,做每个结点的深度记录,但是还是编译错误,显示对rank的引用有歧义,然后就把数组名称由rank改成deep,过了
正确代码:
#include<iostream>
using namespace std;
#define MAX_TREE_SIZE 10010
int parent[MAX_TREE_SIZE]={0};//创建一个结点数组
int deep[MAX_TREE_SIZE]={0};
void initial(int n)//初始化
{
for(int i=0;i<n;i++)
{
parent[i]=-1;
deep[i]=0;
}
}
int find_root(int x)//寻找根结点
{
int x_root=x;
while(parent[x_root]!=-1)// parent[x_root]!=-1说明不是根节点,就一层一层往上找
{
x_root=parent[x_root];
}
return x_root;
}
void combine(int x,int y)//合并集合
{
int x_root=find_root(x);
int y_root=find_root(y);
if(x_root!=y_root)
{
if(deep[x_root]>deep[y_root])
{
parent[y_root]=x_root;
}
else if(deep[x_root]<deep[y_root])
{
parent[x_root]=y_root;
}
else
{
parent[x_root]=y_root;
deep[y_root]++;//结点深度+1
}
}
}
void check(int x,int y)//检查x,y是否在同一集合 ,只要检查他们根节点是不是同一个就好了
{
int x_root=find_root(x);
int y_root=find_root(y);
if(x_root==y_root)//如果x,y的根节点相同,说明他们在同一集合
cout<<"Y"<<endl;
else
cout<<"N"<<endl;
}
int main()
{
int n,m;
cin>>n>>m;//输入,N个元素和 M个操作
initial(n);
int z,x,y;
for(int i=0;i<m;i++)
{
cin>>z>>x>>y;//输入三个整数,进行后续操作
if(z==1)
{
combine(x,y);//将x,y所在集合合并
}
else if(z==2)
{
check(x,y);//输出x,y是否在同一集合
}
else
{
cout<<"输入错误";
exit(0);
}
}
}