Cod sursa(job #322545)

Utilizator mika17Mihai Alex Ionescu mika17 Data 9 iunie 2009 01:25:45
Problema Ciclu Eulerian Scor 0
Compilator cpp Status done
Runda Arhiva educationala Marime 2.87 kb
#include <fstream>
#include <vector>
#include <queue>
#include <bitset>
using namespace std;

ifstream fin("ciclueuler.in");
ofstream fout("ciclueuler.out");

typedef vector< pair<int,int> > vi;
const int NMAX = 100000, MMAX = 500000, start = 0;

int N,M;
vector< pair<int,int> > G[NMAX];

void readGraph() {

     fin>>N>>M;
     
     int x,y;
     for(int i = 0; i < M; ++i) {
             
             fin>>x>>y; --x; --y;
             G[x].push_back( make_pair(y,i) );
             G[y].push_back( make_pair(x,i) );
     }
}

bool isEuler() {
     
     for(int i = 0; i < N; ++i)
             if(G[i].size() & 1) return false;    
     
     queue <int> Q;
     vector<bool> vis(NMAX,0);
     
     Q.push(start);
     vis[start] = 1;
     
     while(!Q.empty()) {
                       
                       int node = Q.front(); Q.pop();
                       
                       for(vi::iterator p = G[node].begin(); p != G[node].end(); ++p)
                       if(!vis[p->first]) {
                                    
                                    Q.push(p->first);
                                    vis[p->first] = 1;
                       }   
     }
     
     for(int i = 0; i < N; ++i)
             if(!vis[i]) return false;
     
     return true;
}

deque < pair<int,int> > edge[NMAX];

void DFS(int K) {
     
     static bitset<NMAX> vis; static bitset <MMAX> vis2;
     
     vis[K] = 1;
    
     for(vi::iterator p = G[K].begin(); p != G[K].end(); ++p)
     if(!vis[p->first]) {

                  edge[K].push_back(make_pair(p->first, p->second ) );
                  edge[p->first].push_back(make_pair(K, p->second) );
                  
                  vis2[ p->second ] = 1;
                  
                  DFS(p->first);
     }
       else if(!vis2[p->second] )
         { edge[K].push_front(make_pair(p->first, p->second) );
           edge[p->first].push_front(make_pair(K,p->second) );
                  
           vis2[ p->second ] = 1;;
          }
}

void getCycle(int K) {
     
     static bitset <MMAX> vis2;
     static int d = 0;
     int node, nr;
     
     if(K == start) if(++d == 2) return;
     fout<<K + 1<<' ';
     bool f = 0;
     while(!edge[K].empty() && !f) {
                         
       node = edge[K].front().first, nr = edge[K].front().second;
       edge[K].pop_front();
       if(!vis2[ nr ]) f = 1;
     }
     while(!edge[K].empty() && !f) {
                         
       node = edge[K].back().first, nr = edge[K].back().second;
       edge[K].pop_back();
       if(!vis2[ nr ]) f = 1;
     }    
     if(f) { vis2[ nr ] = 1; getCycle(node); }
}      

int main() {
    
    readGraph(); 
    if(!isEuler()) fout<<-1;
     else {
          
          DFS(start);
          getCycle(start);
     }

    return 0;   
}