Cod sursa(job #3185699)

Utilizator AleXutzZuDavid Alex Robert AleXutzZu Data 19 decembrie 2023 22:17:46
Problema Ciclu Eulerian Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.3 kb
#include <iostream>
#include <fstream>
#include <stack>
#include <vector>
#include <set>
#include <queue>

struct Graph {
private:
    std::vector<std::multiset<int>> adj;
    int size;

    bool is_connected() {
        std::vector<bool> visited(size + 1, false);
        int cmp = 0;

        for (int i = 1; i <= size; ++i) {
            if (!visited[i]) {
                cmp++;
                visited[i] = true;
                std::queue<int> queue;
                queue.push(i);
                while (!queue.empty()) {
                    int top = queue.front();
                    queue.pop();
                    for (const auto &x: adj[top]) {
                        if (visited[x]) continue;

                        queue.push(x);
                        visited[x] = true;
                    }
                }
            }
        }
        return cmp == 1;
    }

    bool is_eulerian() {
        if (!is_connected()) return false;

        for (int i = 1; i <= size; ++i) {
            if (adj[i].size() % 2 != 0) return false;
        }
        return true;
    }

public:
    explicit Graph(int size) : size(size) {
        adj.resize(size + 1);
    }

    void add_edge(int x, int y) {
        adj[x].insert(y);
        adj[y].insert(x);
    }

    std::vector<int> cycle() {
        std::vector<int> answer;

        if (!is_eulerian()) {
            answer.push_back(-1);
            answer.push_back(-1);
            return answer;
        }

        std::stack<int> stack;
        stack.push(1);

        while (!stack.empty()) {
            int top = stack.top();
            if (adj[top].empty()) {
                answer.push_back(top);
                stack.pop();
            } else {
                int first = *adj[top].begin();
                adj[top].erase(adj[top].begin());
                adj[first].erase(adj[first].lower_bound(top));
                stack.push(first);
            }
        }

        return answer;
    }

};

int main() {
    std::ifstream input("ciclueuler.in");
    std::ofstream output("ciclueuler.out");

    int n, m;
    input >> n >> m;
    Graph graph(n);

    while (m--) {
        int x, y;
        input >> x >> y;
        graph.add_edge(x, y);
    }

    auto cycle = graph.cycle();
    cycle.pop_back();

    for (const auto &x: cycle) output << x << " ";
    return 0;
}