uoj117 欧拉回路(输出欧拉回路模板)

欧拉图判定条件:

无向图:
连通且每个点的度数均为偶数。(可以有孤立点)

有向图:
连通且每个点的入度等于出度。(可以有孤立点)

输出回路:
套圈法,可以搜出没有公共边的若干子回路,并成一个就好了。于是可以用栈把搜到的圈(边)存下来即可。
需要优化一下邻接表(类似Dinic的当前弧优化),复杂度 O ( m )

#include <bits/stdc++.h>
using namespace std;
#define ll long long
#define inf 0x3f3f3f3f
#define N 100010
inline char gc(){
    static char buf[1<<16],*S,*T;
    if(S==T){T=(S=buf)+fread(buf,1,1<<16,stdin);if(T==S) return EOF;}
    return *S++;
}
inline int read(){
    int x=0,f=1;char ch=gc();
    while(ch<'0'||ch>'9'){if(ch=='-') f=-1;ch=gc();}
    while(ch>='0'&&ch<='9') x=x*10+ch-'0',ch=gc();
    return x*f;
}
int n,m;
namespace sol1{
    int h[N],num=1,du[N];
    vector<int>ans;bool vis[N<<1];
    struct edge{
        int to,next;
    }data[N<<2];
    inline void dfs(int x){
        for(int &i=h[x];i;i=data[i].next){
            int y=data[i].to;if(vis[i>>1]) continue;
            vis[i>>1]=1;int tmp=i;dfs(y);ans.push_back(tmp);
        }
    }inline void gao(){
        n=read();m=read();
        for(int i=1;i<=m;++i){
            int x=read(),y=read();du[y]++;du[x]++;
            data[++num].to=y;data[num].next=h[x];h[x]=num;
            data[++num].to=x;data[num].next=h[y];h[y]=num;
        }for(int i=1;i<=n;++i)
            if(du[i]&1){puts("NO");return;}
        for(int i=1;i<=n;++i)
            if(du[i]){dfs(i);break;}
        if(ans.size()!=m){puts("NO");return;}puts("YES");
        reverse(ans.begin(),ans.end());
        for(int i=0;i<ans.size();++i) printf("%d ",ans[i]&1?-(ans[i]>>1):ans[i]>>1);
        puts("");
    }
}
namespace sol2{
    int h[N],num=0,in[N],out[N];
    vector<int>ans;bool vis[N<<1];
    struct edge{
        int to,next;
    }data[N<<1];
    inline void dfs(int x){
        for(int &i=h[x];i;i=data[i].next){
            int y=data[i].to;if(vis[i]) continue;
            vis[i]=1;int tmp=i;dfs(y);ans.push_back(tmp);
        }
    }inline void gao(){
        n=read();m=read();
        for(int i=1;i<=m;++i){
            int x=read(),y=read();in[y]++;out[x]++;
            data[++num].to=y;data[num].next=h[x];h[x]=num;
        }for(int i=1;i<=n;++i)
            if(in[i]!=out[i]){puts("NO");return;}
        for(int i=1;i<=n;++i)
            if(in[i]){dfs(i);break;}
        if(ans.size()!=m){puts("NO");return;}puts("YES");
        reverse(ans.begin(),ans.end());
        for(int i=0;i<ans.size();++i) printf("%d ",ans[i]);puts("");
    }
}
int main(){
//  freopen("a.in","r",stdin);
    if(read()==1) sol1::gao();
    else sol2::gao();
    return 0;
}

猜你喜欢

转载自blog.csdn.net/icefox_zhx/article/details/80753860
今日推荐