Cod sursa(job #2645363)

Utilizator Tudor_PascaTudor Pasca Tudor_Pasca Data 27 august 2020 22:35:21
Problema 2SAT Scor 70
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 3.05 kb
#include <iostream>
#include <fstream>
#include <vector>
#include <stack>

using namespace std;

ifstream in("2sat.in");
ofstream out("2sat.out");

int var, exp, ctc;
int compIndex[100100], answer[100100];
bool emptyGraph;
bool fr[100100], elim[100100];
vector<vector<int>> adj, inv, comp;
stack<int> s;

int NOT(int x)
{
    return (x > var) ? x - var : x + var;
}

void DFS(int node)
{
    fr[node] = true;

    for(auto it : adj[node])
        if(fr[it] == false)
            DFS(it);

    s.push(node);
}

void TDFS(int node, int ctc)
{
    comp[ctc].push_back(node);
    compIndex[node] = ctc;
    fr[node] = false;

    for(auto it : inv[node])
        if(fr[it] == true)
            TDFS(it, ctc);
}

void kosaraju()
{
    for(int i = 1; i <= 2 * var; i++)
        if(fr[i] == false)
            DFS(i);


    while(!s.empty())
    {
        if(fr[s.top()] == true)
        {
            ctc++;
            comp.resize(ctc + 1);

            TDFS(s.top(), ctc);
        }

        s.pop();
    }
}

int findTrueNode()
{
    for(int i = 1; i <= ctc; i++)
    {
        if(elim[comp[i][0]] == true)
            continue;

        //cout << i << '\n';

        bool ok = true;

        for(auto it : comp[i])
        {
            if(ok == false)
                break;

            for(auto vec : adj[it])
            {
                if(ok == false)
                    break;

                if(elim[vec] == false && compIndex[vec] != compIndex[it])
                {
                    //cout << it << ' ' << vec << "\n\n";
                    ok = false;
                }
            }
        }

        //cout << i << ' ' << ok << '\n';

        if(ok == true)
            return i;
    }

    emptyGraph = true;

    return -1;
}

int main()
{
    in >> var >> exp;

    adj.resize(var * 2 + 10);
    inv.resize(var * 2 + 10);

    while(exp--)
    {
        int x, y;

        in >> x >> y;

        if(x < 0)
            x = abs(x) + var;

        if(y < 0)
            y = abs(y) + var;

        adj[NOT(x)].push_back(y);
        adj[NOT(y)].push_back(x);

        inv[y].push_back(NOT(x));
        inv[x].push_back(NOT(y));
    }

    kosaraju();

    for(int i = 1; i <= ctc; i++)
    {
        for(auto it : comp[i])
        {
            if(compIndex[NOT(it)] == i)
            {
                out << -1 << '\n';
                return 0;
            }
        }
    }

    while(!emptyGraph)
    {
        int trueNode = findTrueNode();

        //cout << trueNode << ' ' << "BREAK" << '\n';

        if(trueNode == -1)
            break;

        for(auto it : comp[trueNode])
        {
            elim[it] = true;
            answer[it] = 1;
        }

        int falseNode = compIndex[NOT(comp[trueNode][0])];

        for(auto it : comp[falseNode])
        {
            elim[it] = true;
            answer[it] = 0;
        }
    }


    for(int i = 1; i <= var; i++)
        out << answer[i] << ' ';

    return 0;
}