Cod sursa(job #894489)

Utilizator PatrikStepan Patrik Patrik Data 26 februarie 2013 21:34:59
Problema Ciclu Eulerian Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.42 kb
    #include<cstdio>
    #include<fstream>
    #include<vector>
    #define MAX 100001
    #define pb push_back
    using namespace std;
    int N , M  , grad[MAX] , sol[5*MAX] , ciclu[5*MAX] , k , start;
    bool viz[MAX] , sw , inc[MAX];
    vector<int> g[MAX];
    vector<int>::iterator it;

    void citire();
    void euler();
    void tipar();
    void DF(int nod);

    int main()
    {
        citire();
        euler();
        tipar();
        return 0;
    }

    void citire()
    {
        int x , y;
        ifstream f("ciclueuler.in");
        f>>N>>M;
        for( int i = 1 ; i <= M ; ++i )
        {
            f>>x>>y;
            g[x].pb(y);
            g[y].pb(x);
            grad[x]++;grad[y]++;
        }
    }

    void euler()
    {
        sw = 1;
        for( int i = 1 ; i <= N && sw ; ++i )
            if(grad[i]%2)sw = 0;
        if(!sw)return ;
        for(int i = 1 ; i <= N ; ++i )
            if(!viz[i])DF(i);
        for(int i = 1 ; i <= N ; ++i )
            if(!viz[i])sw = 0;
        if(!sw)return;
        sol[++sol[0]] = 1;
        while(M)
        {
            int i = 1,nod;k = 0;
            for(i = start ; i <=N ; ++i )
                if(grad[i])
                    break;
            start = i;
            while(!g[i].empty())
            {
                nod = *g[i].begin();
                for(it = g[nod].begin() ; it < g[nod].end() ; ++it )
                    if(*it == i)
                    {
                        g[nod].erase(it);
                        break;
                    }
                grad[i]--;grad[nod]--;
                g[i].erase(g[i].begin());
                ciclu[++k] = nod;
                i = nod;
                M--;
            }
            i = 1;
            while(sol[i] != start && i <= sol[0])i++;
            for( int j = sol[0] ; j > i ; j--)
                sol[j+k] = sol[j];
            for( int j = i+1 ; j <= i+k ; ++j )
                sol[j] = ciclu[j-i];
            sol[0] +=k;
        }
    }

    void tipar()
    {
        ofstream g("ciclueuler.out");
        if(!sw)
            g<<-1;
        else
            for( int i = 1 ; i < sol[0] ; ++i )
                g<<sol[i]<<" ";
    }


    void DF(int nod)
    {
        viz[nod] = 1;
        for( vector<int>::iterator it = g[nod].begin() ; it < g[nod].end() ; ++it )
            if(!viz[*it])DF(*it);
    }