Cod sursa(job #882160)

Utilizator andonemadalin andone Data 18 februarie 2013 22:07:17
Problema Ciclu Eulerian Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.1 kb
#include <fstream>
#include<vector>
#define Dmax 100005
using namespace std;

ifstream intrare("ciclueuler.in");
ofstream iesire("ciclueuler.out");

int n, m;
int d[Dmax];
int viz[Dmax];
vector<int>G[Dmax];
int total;
struct nod{int vf; struct nod * urm;};
typedef struct nod * Lista;
Lista C1, C2, sfC1, sfC2;

void citire();
void dfs(int x);
void determinare_eulerian();
bool conex();
bool gradepare();
int ciclu(int x, Lista &inc, Lista &sf);
void afisare();

int main()
{
	citire();
	if (conex() && gradepare())
	{
		determinare_eulerian();
		afisare();
	}
	else
		iesire <<-1<<'\n';
	iesire.close();
	return 0;
}
void citire()
{
    int x, y, i;
    intrare>>n>>m;
    for(i=1;i<=m;i++)
    {
        intrare>>x>>y;
        d[x]++; d[y]++;
        G[x].push_back(y);
        G[y].push_back(x);
    }
}
void dfs(int x)
{
    int i;
    viz[x]=true;
    for(i=0;i<G[x].size();i++)
        if(!viz[G[x][i]])
            dfs(G[x][i]);
}
bool gradepare()
{
	int i;
	for(i = 1; i <= n; i++)
		if (d[i]%2)
			return 0;
	return 1;
}
bool conex()
{
  int x, i;
  for(x = 1; x <= n && !d[x]; x++);
    if (x >= n)
      return 0;
    dfs(x);
    for(i = 1; i <=n; i++)
      if (!viz[i] && d[i])
        return 0;
    return 1;
}
void determinare_eulerian()
{
	int x,nr2;
	Lista p,q;
	for(x=1;x<=n&&!d[x];x++);
	total=ciclu(x,C1,sfC1);
	while(total!=m)
	{
		for(p=C1;!d[p->vf];p=p->urm);
		nr2=ciclu(p->vf,C2,sfC2);
		q=p->urm;
		p->urm=C2->urm;
		sfC2->urm=q;
		total+=nr2;
	}
}
int ciclu(int x, Lista &inc, Lista &sf)
{
	Lista p;
	int y,uvf,i,j,lg = 0; 
	p=new nod;
	p->vf=x;
	p->urm=NULL;
	inc=sf=p;
	do
	{
		uvf=sf->vf;
		for(i=0;i<G[uvf].size();i++)
			if(G[uvf][i])
				break;
		y=G[uvf][i];
		p=new nod;
		p->vf=y;
		p->urm=NULL;
		sf->urm=p;
		sf=p;
		lg++; 
		G[uvf][i]=0;
		for(j=0;j<G[y].size();j++)
			if(G[y][j]==uvf)
			{
				G[y][j]=0;
				break;
			}
		d[uvf]--;d[y]--;
	}
	while(y!=x);
	return lg;
}
void afisare()
{
    Lista p;
    for(p=C1; p;p=p->urm)
        iesire<<p->vf<<' ';
    iesire<<'\n';
}