码迷,mamicode.com
首页 > 其他好文 > 详细

poj 2762

时间:2018-08-11 17:46:21      阅读:148      评论:0      收藏:0      [点我收藏+]

标签:||   bool   etc   for   fine   struct   har   pre   路径   

Tarjan + Topsort
Tarjan 缩点
Topsort 判断

Topsort 判断:
在DAG中
若初始状态下存在多于1个入度为0的点
则说明这些 入度为0的点之间不会有路径可达
若不存在入度为0的点,则状态为Yes
若只存在1个入度为0的点,将该点指出的边删除
继续上述判断

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>

const int N = 1010, M = N * 6;

#define gc getchar()

inline int read() {
    int x = 0; char c = gc;
    while(c < 0 || c > 9) c = gc;
    while(c >= 0 && c <= 9) x = x * 10 + c - 0, c = gc;
    return x;
}

int head[N], head_2[N], cnt;
struct Node {int u, v, nxt;};
Node G[M], E[M];
int In[N], n, m;
int Low[N], Dfn[N], Stack[N], Belong[N], Scc, Tim, topp;
bool vis[N];

inline void Add_1(int u, int v) {G[++ cnt].v = v; G[cnt].nxt = head[u]; head[u] = cnt;}
inline void Add_2(int u, int v) {E[++ cnt].v = v; E[cnt].nxt = head_2[u]; head_2[u] = cnt; In[v] ++;}

inline void Clear() {
    memset(head, -1, sizeof head);
    memset(head_2, -1, sizeof head_2);
    memset(In, 0, sizeof In);
    memset(Low, 0, sizeof Low);
    memset(Dfn, 0, sizeof Dfn);
    memset(vis, 0, sizeof vis);
    topp = cnt = Scc = Tim = 0;
}

inline void Init() {
    n = read(), m = read();
    for(int i = 1; i <= m; i ++) Add_1(read(), read());
}

void Tarjan(int x) {
    Low[x] = Dfn[x] = ++ Tim;
    Stack[++ topp] = x; vis[x] = 1;
    for(int i = head[x]; ~ i; i = G[i].nxt) {
        int v = G[i].v;
        if(!Dfn[v]) {
            Tarjan(v);
            Low[x] = std:: min(Low[x], Low[v]);
        } else if(vis[v]) Low[x] = std:: min(Low[x], Low[v]);
    }
    if(Dfn[x] == Low[x]) {
        vis[x] = 0, Belong[x] = ++ Scc;
        while(Stack[topp] != x) {
            vis[Stack[topp]] = 0, Belong[Stack[topp]] = Scc;
            topp --;
        } topp --;
    }
}

inline void Rebuild() {
    cnt = 0;
    for(int u = 1; u <= n; u ++)
        for(int i = head[u]; ~ i; i = G[i].nxt)
            if(Belong[u] != Belong[G[i].v]) Add_2(Belong[u], Belong[G[i].v]);
}

void Topsort() {
    if(Scc == 1) {puts("Yes"); return ;}
    int Ans(0), flag;
    for(int i = 1; i <= Scc; i ++) if(!In[i]) Ans ++, flag = i;
    if(Ans > 1) {puts("No"); return ;}
    int temp = Scc;
    for(; temp; temp --) {
        Ans = 0;
        for(int i = head_2[flag]; ~ i; i = E[i].nxt) {
            int v = E[i].v;
            In[v] --;
            if(!In[v]) Ans ++, flag = v;
        }
        if(Ans > 1) {puts("No"); return ;}
        if(!Ans) {puts("Yes"); return ;}
    }
    puts("Yes"); return ;
}

void Work() {
    Clear();
    Init();
    for(int i = 1; i <= n; i ++) if(!Dfn[i]) Tarjan(i);
    Rebuild();
    Topsort();
}

int main() {
    int t = read();
    for(; t; t --, Work());
    return 0;
}

 

    

poj 2762

标签:||   bool   etc   for   fine   struct   har   pre   路径   

原文地址:https://www.cnblogs.com/shandongs1/p/9460406.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!