CF962F- Simple Cycles Edges (点双连通分量)

题解:我们判断是否是一个简单环,我们可以判断缩点然后之间经过了哪些边判断一下即可,注意一个很特殊的就是边如果点只有一个的话不是环,并且要求边数和点数相同才是一个环。

#include<iostream>
#include<cstring>
#include<algorithm>
#include<queue>
#include<vector>
#include<cstdio>
#include<cmath>
#include<set>
#include<map>
#include<cstdlib>
#include<ctime>
#include<stack>
#include<bitset>
using namespace std;
#define mes(a) memset(a,0,sizeof(a))
#define rep(i,a,b) for(i = a; i <= b; i++)
#define dec(i,a,b) for(i = b; i >= a; i--)
#define fi first
#define se second
#define ls rt<<1
#define rs rt<<1|1
#define mid (L+R)/2
#define lson ls,L,mid
#define rson rs,mid+1,R
typedef double db;
typedef long long int ll;
typedef pair<int,int> pii;
typedef unsigned long long ull;
const ll inf = 0x3f3f3f3f;
const int mx = 1e5+5;
const int x_move[] = {1,-1,0,0,1,1,-1,-1};
const int y_move[] = {0,0,1,-1,1,-1,1,-1};
int n,m;
vector<pii>g[mx];
int pre[mx],low[mx],sccno[mx];
int bj[mx];
int	vsize[mx];
vector<int>e;
stack<pii>s;
bool vis[mx];
set<int>st;
int dfn,cnt;
void dfs(int u,int fa){
	pre[u] = low[u] = ++dfn;
	for(auto it: g[u]){
		int v = it.fi;
		int i = it.se;
		if(vis[i])
			continue;
		vis[i] = 1;
		s.push(it);
		if(!pre[v]){
			dfs(v,u);
			low[u] = min(low[u],low[v]);
			if(low[v]>=pre[u]){
				cnt++;
				e.clear();
				while(1){
					pii x = s.top();
					s.pop();
					if(bj[x.fi]!=cnt){
						vsize[cnt]++;
						bj[x.fi] = cnt;
					}
					sccno[x.se] = cnt;
					e.push_back(x.se);
					if(x.se == i)
						break;
				}
				if(vsize[cnt]>1 && e.size()==vsize[cnt]){
					for(int j = 0; j < e.size(); j++)
						st.insert(e[j]);
					
				}
			}
		}
		else if(v!=fa)
			low[u] = min(low[u],pre[v]);
	}
}
int main(){
	int t,q,ca = 1;
	scanf("%d%d",&n,&m);
	for(int i = 1; i <= m; i++){
		int u,v;
		scanf("%d%d",&u,&v);
		g[u].push_back(make_pair(v,i));
		g[v].push_back(make_pair(u,i));
	}
	for(int i = 1; i <= n; i++)
		if(!pre[i])
			dfs(i,i);
	cout<<st.size()<<endl;
	for(auto it = st.begin(); it != st.end(); ){
		printf("%d",*it);
		it++;
		if(it==st.end())
			printf("\n");
		else
			printf(" ");
	}
	return 0;
}

猜你喜欢

转载自blog.csdn.net/a1325136367/article/details/79920839