zoukankan      html  css  js  c++  java
  • tarjan

    tarjan
    目的:求极大强联通分量
    复杂度:O(n+m);
    dfn[]表示这个点是第几次被dfs到的
    low[]指极大强联通分量中最先被dfs到的,如果dfn[]==low[]那么它就是极大强联通分量中的祖先
    用栈储存

      1 #include<iostream>
      2 #include<cstdio>
      3 #include<queue>
      4 #include<algorithm>
      5 #include<cmath>
      6 #include<ctime>
      7 #include<set>
      8 #include<map>
      9 #include<stack>
     10 #include<cstring>
     11 #define inf 2147483647
     12 #define ls rt<<1
     13 #define rs rt<<1|1
     14 #define lson ls,nl,mid,l,r
     15 #define rson rs,mid+1,nr,l,r
     16 #define N 100010
     17 #define For(i,a,b) for(int i=a;i<=b;i++)
     18 #define p(a) putchar(a)
     19 #define g() getchar()
     20 
     21 using namespace std;
     22 struct node{
     23     int n;
     24     node *next;
     25 }*e[1010];
     26 
     27 int dfn[1010],low[1010];
     28 stack<int>s;
     29 bool vis[1010];
     30 int now,tot;
     31 int x,y;
     32 int n,m;
     33 void in(int &x){
     34     int y=1;
     35     char c=g();x=0;
     36     while(c<'0'||c>'9'){
     37         if(c=='-')y=-1;
     38         c=g();
     39     }
     40     while(c<='9'&&c>='0'){
     41         x=(x<<1)+(x<<3)+c-'0';c=g();
     42     }
     43     x*=y;
     44 }
     45 void o(int x){
     46     if(x<0){
     47         p('-');
     48         x=-x;
     49     }
     50     if(x>9)o(x/10);
     51     p(x%10+'0');
     52 }
     53 
     54 void push(int x,int y){
     55     node *p;
     56     p=new node();
     57     p->n=y;
     58     if(e[x]==0)
     59         e[x]=p;
     60     else{
     61         p->next=e[x]->next;
     62         e[x]->next=p;
     63     }
     64 }
     65 
     66 void tarjan(int x){
     67     dfn[x]=low[x]=++tot;
     68     vis[x]=true;
     69     s.push(x);
     70     for(node *i=e[x];i;i=i->next){
     71         if(!dfn[i->n]){
     72             tarjan(i->n);
     73             low[x]=min(low[x],low[i->n]);
     74         }
     75         else 
     76             if(vis[i->n])
     77                 low[x]=min(low[x],dfn[i->n]);
     78     }
     79         if(low[x]==dfn[x]){
     80             do{
     81                 now=s.top();
     82                 o(now);p(' ');
     83                 s.pop();
     84                 vis[now]=false;
     85             }while(x!=now);
     86             p('
    ');
     87         }        
     88     
     89 }
     90 
     91 int main(){
     92     in(n);in(m);
     93     For(i,1,m){
     94         in(x);in(y);
     95         push(x,y);
     96     }
     97     For(i,1,n)
     98         if(!dfn[i])
     99             tarjan(i);
    100     return 0;
    101 }
    View Code
  • 相关阅读:
    Python/WSGI 应用快速入门--转
    汇编题目:数字转字符,并在窗口上显示出来
    汇编题目:在窗口上显示Welcome to masm!
    VBA中的函数Timer用法
    用VBA计算两个日期之间的工作日(去掉周末两天)
    VBA记录当前系统时间并精确到毫秒
    上海房产税免征--积分或居住证
    学习汇编语言
    “Hello World”—— 第一个汇编程序
    汇编程序设计上机步骤
  • 原文地址:https://www.cnblogs.com/war1111/p/10338254.html
Copyright © 2011-2022 走看看