[POI2001]和平委员会

Posted zcr-blog

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[POI2001]和平委员会相关的知识,希望对你有一定的参考价值。

2-SAT裸题

如果不会2-SAT,点

总结一下2-SAT其实就是若a则非b这样的形式,建一条边即可。

#include <bits/stdc++.h>
using namespace std;
const int N = 16010;
const int M = 40010;
struct node{
    int pre, to;
    node() {
        pre = to = 0;
    }
    node(int _pre, int _to) {
        pre = _pre;
        to = _to;
    }
}edge[M];
int head[N], tot;
int n, m;
int dfn[N], low[N], stk[N], top, dep, c, col[N];
bool vis[N];
void tarjan(int x) {
    dfn[x] = low[x] = ++dep;
    stk[++top] = x;
    vis[x] = 1;
    for (int i = head[x]; i; i = edge[i].pre) {
        int y = edge[i].to;
        if (!dfn[y]) {
            tarjan(y);
            low[x] = min(low[x], low[y]);
        } else if (vis[y]) {
            low[x] = min(low[x], dfn[y]);
        }
    }
    if (low[x] == dfn[x]) {
        c++;
        col[x] = c;
        vis[x] = 0;
        while (stk[top] != x) {
            col[stk[top]] = c;
            vis[stk[top]] = 0;
            top--;
        }
        top--;
    }
}
inline void add(int u, int v) {
    edge[++tot] = node(head[u], v);
    head[u] = tot;
}
inline int read() {
    int ret = 0, f = 1;
    char ch = getchar();
    while (!isdigit(ch)) {
        if (ch == -) f = -1;
        ch = getchar();
    }
    while (isdigit(ch)) {
        ret = (ret << 1) + (ret << 3) + ch - 0;
        ch = getchar();
    }
    return ret * f;
}
inline int FP(int x) {
    if (x % 2) return x + 1;
    return x - 1;
}
void write(int x) {
    if (x > 9) write(x / 10);
    putchar(x % 10 + 0);
}
inline void print(int x) {
    if (x < 0) {
        putchar(-);
        x = -x;
    }
    write(x);
    putchar(
);
}
int main() {
    n = read(); m = read();
    for (int i = 1, a, b; i <= m; ++i) {
        a = read();
        b = read();
        add(a, FP(b));
        add(b, FP(a));
    }
    for (int i = 1; i <= n << 1; i++) {
        if (!dfn[i]) {
            tarjan(i);
        }
    }
    for (int i = 1; i <= n << 1; i += 2) {
        if (col[i] == col[i + 1]) {
            puts("NIE");
            exit(0);
        }
    }
    for (int i = 1; i <= n << 1; i += 2) {
        if (col[i] < col[i + 1]) {
            print(i); 
        } else {
            print(i + 1);
        }
    }
    return 0;
}

 

以上是关于[POI2001]和平委员会的主要内容,如果未能解决你的问题,请参考以下文章

[POI2001]和平委员会

[Poi2001]和平委员会 理解

HIT 1917 2—SAT

P2444 [POI2000]病毒

[Poi2000]病毒

Poi2000病毒