Cod sursa(job #2821343)

Utilizator XeinIonel-Alexandru Culea Xein Data 22 decembrie 2021 14:22:29
Problema Ciclu Eulerian Scor 10
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.63 kb
#include <fstream>
#include <vector>
#include <utility>
 
using namespace std;
 
std::ifstream f("ciclueuler.in");
std::ofstream g("ciclueuler.out");
int N, M, nodStart;
vector<vector< pair<int, pair<bool, int>> >> Adiacenta;  // {nod vecin, {muchie de intoarcere?, indexul muchiei in lista lui nod_vecin}}
bool vizitat[100009];
vector<int> Solutie;
 
 
void DFS(int nodCurent, int nodTata)
{
    vizitat[nodCurent] = true;
    for (auto& vecin : Adiacenta[nodCurent])
    {
        if (!vizitat[vecin.first])
            DFS(vecin.first, nodCurent);
        else if (vecin.first != nodTata)
            vecin.second.first = 1;
    }
}
 
void Fleury()
{
    Solutie.reserve(M);
    int nodCurent = nodStart;
 
    for (;;)
    {
        Solutie.push_back(nodCurent);
        
        while (Adiacenta[nodCurent].size() > 0 && Adiacenta[nodCurent].back().first == 0)
            Adiacenta[nodCurent].pop_back();
        
        if (Adiacenta[nodCurent].size() > 0)
        {
            int nodUrmator = Adiacenta[nodCurent].back().first;
            int idx = Adiacenta[nodCurent].back().second.second;
            Adiacenta[nodCurent].back().first = 0;
            Adiacenta[nodUrmator][idx].first = 0;

            nodCurent = nodUrmator;
        }
        else
            break;
    }
 
    Solutie.pop_back();
}
 
int main()
{
    f >> N >> M;
    Adiacenta.resize(N + 1);
    for (int x, y, i = 0; i < M; ++i)
    {
        f >> x >> y;
        nodStart = x;
        if (x != y)
        {
            Adiacenta[x].push_back({y, {0, (int)Adiacenta[y].size()}});
            Adiacenta[y].push_back({x, {0, (int)Adiacenta[x].size() - 1}});
        }
        else
        {
            Adiacenta[x].push_back({y, {0, (int)Adiacenta[y].size() + 1}});
            Adiacenta[y].push_back({x, {0, (int)Adiacenta[x].size() - 1}});
        }
    }

    DFS(nodStart, 0);

    for (auto& lista : Adiacenta)
    {
        int st = 0, dr = lista.size() - 1;
        while (st < dr)
        {
            if (lista[st].second.first)
            {
                std::swap(lista[st], lista[dr]);
                auto& muchie1 = lista[st];
                auto& muchie2 = lista[dr];
                Adiacenta[muchie1.first][muchie1.second.second].second.second = st;
                Adiacenta[muchie2.first][muchie2.second.second].second.second = dr;
                --dr;
            }
            else
                ++st;
        }
    }

    Fleury();
 
    if (Solutie.size() != M)
        g << -1;
    else
        for (auto nod : Solutie)
            g << nod << ' ';
 
    return 0;
}