Cod sursa(job #2446546)

Utilizator CharacterMeCharacter Me CharacterMe Data 9 august 2019 16:59:01
Problema 2SAT Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.24 kb
#include <bits/stdc++.h>

using namespace std;
int n, m, i, j, cnt, v;
int ctc[200001], sol[200001], inv[200001];
pair<int, int> p[200001];
vector<int> graph[200001];
vector<int> ctclist[200001];
stack<int> s;
bool check[200001], ins[200001], done[200001];

void read();
bool solve();
void dfs(int node);
bool turn(int c, int val);
int up(int node);
int other(int node);
int main()
{
    freopen("2sat.out", "w", stdout);
    read();
    if(!solve())printf("-1");
    else for(i=1; i<=n; ++i) printf("%d ", sol[i]);
    return 0;
}
void read(){
    freopen("2sat.in", "r", stdin);
    scanf("%d%d", &n, &m);
    for(i=1; i<=m; ++i){
        int x, y;
        scanf("%d%d", &x, &y);
        graph[up(-x)].push_back(up(y));
        graph[up(-y)].push_back(up(x));
    }
    return;
}
bool solve(){
    for(i=1; i<=2*n; ++i) if(!check[i]) dfs(i);
    for(i=1; i<=n; ++i) if(ctc[i]==ctc[other(i)]) return false;
    for(i=v; i>=1; --i) if(!done[i]){
        done[i]=done[inv[i]]=true;
        for(auto j:ctclist[i]){
            sol[j]=0;
            sol[other(j)]=1;
        }
    }
    return true;
}
void dfs(int node){
    check[node]=ins[node]=true; ++cnt;
    p[node]={cnt, cnt}; s.push(node);
    for(auto i:graph[node]){
        if(!check[i]){
            dfs(i);
            p[node].second=min(p[node].second, p[i].second);
        }
        else if(ins[i]) p[node].second=min(p[node].second, p[i].first);
    }
    if(p[node].first==p[node].second){
        ++v;
        while(s.top()!=node) {
            ins[s.top()]=false;
            ctclist[v].push_back(s.top());
            ctc[s.top()]=v;
            if(ctc[other(s.top())]) {
                inv[ctc[s.top()]]=ctc[other(s.top())];
                inv[ctc[other(s.top())]]=ctc[s.top()];
            }
            s.pop();
        }
        ins[s.top()]=false;
        ctclist[v].push_back(s.top());
        ctc[s.top()]=v;
        if(ctc[other(s.top())]) {
            inv[ctc[s.top()]]=ctc[other(s.top())];
            inv[ctc[other(s.top())]]=ctc[s.top()];
        }
        s.pop();
    }
    return;
}
int up(int node){
    if(node<0) return n-node;
    return node;
}
int other(int node){
    if(node>n) return node-n;
    return node+n;
}