Codeforces Round #541 (Div. 2) F. Asya And Kittens
链接:https://codeforces.com/contest/1131/problem/F
题意:有一个由1~n构成的长度为n的序列,相邻两数不连通,经过n-1次操作,整个序列是连通的,每次操作只能将相邻两块进行连通,给出每次操作时相邻两块中的数字,输出原序列
思路:并查集,根据大佬的题解,用类似链表的方法进行连接
代码:(转载自https://www.cnblogs.com/ZERO-/p/10426473.html)
1 //F-双向链表(模拟)+并查集 2 #include<bits/stdc++.h> 3 using namespace std; 4 typedef long long ll; 5 const int maxn=15*1e5+10; 6 7 int l[maxn],r[maxn],nex[maxn],root[maxn]; 8 9 int findr(int x)//递归并查集 10 { 11 if(root[x]==x) return x; 12 return root[x]=findr(root[x]); 13 } 14 15 int main() 16 { 17 int n,u,v; 18 cin>>n; 19 for(int i=1;i<=n;i++) 20 root[i]=l[i]=r[i]=i;//初始化 21 while(n>1){ 22 n--; 23 cin>>u>>v; 24 u=findr(u); 25 v=findr(v); 26 root[v]=u;//并查集合并 27 nex[r[u]]=l[v];//当前u的最右端的节点与v的最左端的节点相连 28 r[u]=r[v];//将u的最右端节点更新为v的最右端节点 29 } 30 u=l[findr(1)];//找到头节点 31 while(u){ 32 cout<<u<<" "; 33 u=nex[u];//按照连接顺序输出 34 } 35 }
备注:第一次做并查集的题目,感觉对递归和链表的要求挺大的,感谢这篇博客->https://blog.csdn.net/liuyang981122/article/details/81530014 ,写的非常清晰明白,留待以后继续学习
————————————————
心里有光,哪儿都美
心里有光,哪儿都美