zoukankan      html  css  js  c++  java
  • HDU 2460 Network(桥+LCA)

    http://acm.hdu.edu.cn/showproblem.php?pid=2460

    题意:
    给出图,求每次增加一条边后图中桥的数量。

    思路:

    先用tarjan算法找出图中所有的桥,如果lowv>pre[u],那么u—v就是桥,此时可以标记一下v。

    之后就是利用LCA,找到两个节点的公共祖先,在这条路径上的桥就不再是桥了。(此时就相当于这些桥组成的树,可以在脑海中缩点)

      1 #include<iostream>
      2 #include<algorithm>
      3 #include<cstring>
      4 #include<cstdio>
      5 #include<sstream>
      6 #include<vector>
      7 #include<stack>
      8 #include<queue>
      9 #include<cmath>
     10 #include<map>
     11 #include<set>
     12 using namespace std;
     13 typedef long long ll;
     14 typedef pair<int,int> pll;
     15 const int INF = 0x3f3f3f3f;
     16 const int maxn=100000+5;
     17 
     18 int n, m;
     19 int tot;
     20 int cnt;
     21 int head[maxn];
     22 int dfs_clock;
     23 int pre[maxn];
     24 int low[maxn];
     25 int isbridge[maxn];
     26 int p[maxn];
     27 
     28 struct node
     29 {
     30     int v;
     31     int next;
     32 }e[400000+5];
     33 
     34 void addEdge(int u, int v)
     35 {
     36     e[tot].v=v;
     37     e[tot].next=head[u];
     38     head[u]=tot++;
     39 }
     40 
     41 void init()
     42 {
     43     cnt=0;
     44     dfs_clock=0;
     45     memset(pre,0,sizeof(pre));
     46     memset(isbridge,0,sizeof(isbridge));
     47     for(int i=1;i<=n;i++)  p[i]=i;
     48 }
     49 
     50 int dfs(int u, int fa)
     51 {
     52     int lowu=pre[u]=++dfs_clock;
     53     for(int i=head[u];i!=-1;i=e[i].next)
     54     {
     55         int v=e[i].v;
     56         if(!pre[v])
     57         {
     58             p[v]=u;
     59             int lowv=dfs(v,u);
     60             lowu=min(lowu,lowv);
     61             if(lowv>pre[u])   {cnt++;isbridge[v]=1;}
     62         }
     63         else if(pre[v]<pre[u] && v!=fa)
     64             lowu=min(lowu,pre[v]);
     65     }
     66     return low[u]=lowu;
     67 }
     68 
     69 int LCA(int u, int v)
     70 {
     71     while(low[u]>low[v])
     72     {
     73         if(isbridge[u])  {cnt--;isbridge[u]=0;}
     74         u=p[u];
     75     }
     76     while(low[v]>low[u])
     77     {
     78         if(isbridge[v])  {cnt--;isbridge[v]=0;}
     79         v=p[v];
     80     }
     81     while(u!=v)
     82     {
     83         if(isbridge[u])  {cnt--;isbridge[u]=0;}
     84         if(isbridge[v])  {cnt--;isbridge[v]=0;}
     85         u=p[u];
     86         v=p[v];
     87     }
     88 }
     89 
     90 int main()
     91 {
     92     //freopen("in.txt","r",stdin);
     93     int kase=0;
     94     while(~scanf("%d%d",&n,&m))
     95     {
     96         if(n==0 && m==0)  break;
     97         tot=0;
     98         memset(head,-1,sizeof(head));
     99         while(m--)
    100         {
    101             int u,v;
    102             scanf("%d%d",&u,&v);
    103             addEdge(u,v);
    104             addEdge(v,u);
    105         }
    106         init();
    107         dfs(1,-1);
    108         int q;
    109         scanf("%d",&q);
    110         printf("Case %d:
    ",++kase);
    111         while(q--)
    112         {
    113             int u,v;
    114             scanf("%d%d",&u,&v);
    115             LCA(u,v);
    116             printf("%d
    ",cnt);
    117         }
    118         printf("
    ");
    119     }
    120     return 0;
    121 }
  • 相关阅读:
    前端插件资源
    wPaint在线绘图插件
    【剑指offer】数字数组中只出现一次(2)
    系统,特别是慢查找
    Asp.Netserver控制发展Grid实现(一个)UI转让
    JAVA连接ACCESS、MYSQL、SQLSEVER、ORACLE数据库
    u_boot启动过程中的具体分析(1)
    免费是移动互联网的第一个念头
    进入公司第五届、六个月
    Windows平台Oracle使用USE_SHARED_SOCKET角色
  • 原文地址:https://www.cnblogs.com/zyb993963526/p/7297384.html
Copyright © 2011-2022 走看看