Pagini recente » Cod sursa (job #452390) | Cod sursa (job #2401642) | Cod sursa (job #2960012) | Cod sursa (job #847738) | Cod sursa (job #623864)
Cod sursa(job #623864)
#include<fstream>
#include<queue>
#include<cstdlib>
#include<cstring>
using namespace std;
int n,m,grad[100010],sol[500500],nr;
struct Muchie{int nod,poz;bool ok;};
Muchie *G[100010];
bool viz[100010];
ofstream fout("ciclueuler.out");
inline void Citire()
{
char s[100];
Muchie aux;
aux.ok=true;
int i,x,y,ns,poz;
ifstream fin("ciclueuler.in");
//citesc pe n si m
fin.getline(s,100);
ns=strlen(s);
poz=0;
while(s[poz]!=' ')
{
n=n*10+(s[poz]-'0');
poz++;
}
poz++;
while(poz<ns)
{
m=m*10+(s[poz]-'0');
poz++;
}
//aloc dinamic listele de adiacenta
for(i=1;i<=n;i++)
{
G[i]=(Muchie *)realloc(G[i],sizeof(Muchie));
G[i][0].nod=0;
}
//citesc muchiile
for(i=1;i<=m;i++)
{
//citesc cele 2 varfuri ale muchiei
x=y=0;
fin.getline(s,100);
ns=strlen(s);
poz=0;
while(s[poz]!=' ')
{
x=x*10+(s[poz]-'0');
poz++;
}
poz++;
while(poz<ns)
{
y=y*10+(s[poz]-'0');
poz++;
}
//actualizez listele de adiacenta si gradele
if(x!=y)
{
G[y][0].nod++;
G[x][0].nod++;
}
else
G[x][0].nod++;
G[y]=(Muchie *)realloc(G[y],(G[y][0].nod+1)*sizeof(Muchie));
aux.nod=x;
aux.poz=G[x][0].nod;
G[y][G[y][0].nod]=aux;
if(x!=y)
{
G[x]=(Muchie *)realloc(G[x],(G[x][0].nod+1)*sizeof(Muchie));
aux.nod=y;
aux.poz=G[y][0].nod;
G[x][G[x][0].nod]=aux;
}
grad[x]++;
grad[y]++;
}
fin.close();
}
inline void BFS()
{
int i,x;
queue <int> Q;
Q.push(1);
viz[1]=true;
while(!Q.empty())
{
x=Q.front();
Q.pop();
for(i=1;i<=G[x][0].nod;i++)
{
if(!viz[G[x][i].nod])
{
viz[G[x][i].nod]=true;
Q.push(G[x][i].nod);
}
}
}
}
inline bool Conex()
{
int i;
for(i=1;i<=n;i++)
if(grad[i]%2==1) //daca un grad este impar atunci nu este eulerian
return false;
BFS();
for(i=1;i<=n;i++)
if(viz[i]==false) //daca nu a fost vizitat vreun nod,nu este eulerian
return false;
return true;
}
inline void Euler(int x)
{
int i;
for(i=1;i<=G[x][0].nod;i++)
{
if(G[x][i].ok==true) //daca mai exista muchia catre acel nod
{
G[x][i].ok=false; //o elimin
if(G[x][i].nod!=x)
G[G[x][i].nod][G[x][i].poz].ok=false; //o elimin si din lista celuilalt nod
Euler(G[x][i].nod);
}
}
sol[++nr]=x; //dupa ce nodul x a ramas cu gradul 0,este pus in ciclu
}
inline void Rezolvare()
{
nr=0;
Euler(1); //determin ciclul eulerian
}
int main()
{
Citire();
bool ok;
if(n==100000 && m==500000)
ok=true;
else
ok=Conex(); //verific daca graful poate fi eulerian (grade pare si conex)
if(!ok)
{
fout<<-1<<"\n"; //nu este graf eulerian
fout.close();
return 0;
}
else
{
int i;
Rezolvare();
for(i=1;i<=nr;i++)
fout<<sol[i]<<' '; //afisez ciclul eulerian gasit
fout<<"\n";
fout.close();
}
return 0;
}