zoukankan      html  css  js  c++  java
  • HDU 4612 Warm up

    Warm up

    Time Limit: 5000ms
    Memory Limit: 65535KB
    This problem will be judged on HDU. Original ID: 4612
    64-bit integer IO format: %I64d      Java class name: Main
      N planets are connected by M bidirectional channels that allow instant transportation. It's always possible to travel between any two planets through these channels.
      If we can isolate some planets from others by breaking only one channel , the channel is called a bridge of the transportation system.
    People don't like to be isolated. So they ask what's the minimal number of bridges they can have if they decide to build a new channel.
      Note that there could be more than one channel between two planets.
     

    Input

      The input contains multiple cases.
      Each case starts with two positive integers N and M , indicating the number of planets and the number of channels.
      (2<=N<=200000, 1<=M<=1000000)
      Next M lines each contains two positive integers A and B, indicating a channel between planet A and B in the system. Planets are numbered by 1..N.
      A line with two integers '0' terminates the input.
     

    Output

      For each case, output the minimal number of bridges after building a new channel in a line.
     

    Sample Input

    4 4
    1 2
    1 3
    1 4
    2 3
    0 0

    Sample Output

    0

    Source

     
    解题:类似于network那题。。。边双连通+树的直径
    此题严重爆栈。。。只能用微软的编译器
     
     1 #pragma comment(linker, "/STACK:102400000,102400000")
     2 #include <iostream>
     3 #include <queue>
     4 #include <cstdio>
     5 #include <cstring>
     6 #include <stack>
     7 using namespace std;
     8 const int maxn = 200010;
     9 struct arc{
    10     int to,next;
    11     arc(int x = 0,int y = -1){
    12         to = x;
    13         next = y;
    14     }
    15 }e[4000000];
    16 int head[maxn],hd[maxn],dfn[maxn],low[maxn],belong[maxn];
    17 int scc,idx,tot,n,m,d[maxn];
    18 bool instack[maxn];
    19 stack<int>stk;
    20 void add(int *head,int u,int v){
    21     e[tot] = arc(v,head[u]);
    22     head[u] = tot++;
    23 }
    24 void tarjan(int u,int fa){
    25     dfn[u] = low[u] = ++idx;
    26     instack[u] = true;
    27     stk.push(u);
    28     bool flag = true;
    29     for(int i = head[u]; ~i; i = e[i].next){
    30         if(e[i].to == fa && flag){
    31             flag = false;
    32             continue;
    33         }
    34         if(!dfn[e[i].to]){
    35             tarjan(e[i].to,u);
    36             low[u] = min(low[u],low[e[i].to]);
    37         }else if(instack[e[i].to]) low[u] = min(low[u],dfn[e[i].to]);
    38     }
    39     if(low[u] == dfn[u]){
    40         scc++;
    41         int v;
    42         do{
    43             instack[v = stk.top()] = false;
    44             stk.pop();
    45             belong[v] = scc;
    46         }while(v != u);
    47     }
    48 }
    49 void init(){
    50     for(int i = 0; i < maxn; ++i){
    51         head[i] = hd[i] = -1;
    52         belong[i] = low[i] = dfn[i] = 0;
    53         instack[i] = false;
    54     }
    55     idx = scc = tot = 0;
    56     while(!stk.empty()) stk.pop();
    57 }
    58 queue<int>q;
    59 int bfs(int u){
    60     while(!q.empty()) q.pop();
    61     memset(d,-1,sizeof(d));
    62     d[u] = 0;
    63     q.push(u);
    64     while(!q.empty()){
    65         u = q.front();
    66         q.pop();
    67         for(int i = hd[u]; ~i; i = e[i].next){
    68             if(d[e[i].to] == -1){
    69                 d[e[i].to] = d[u] + 1;
    70                 q.push(e[i].to);
    71             }
    72         }
    73     }
    74     int maxV = 0,idx = u;
    75     for(int i = 1; i <= scc; ++i)
    76         if(d[i] > maxV) maxV = d[idx = i];
    77     return idx;
    78 }
    79 int main(){
    80     int u,v;
    81     while(scanf("%d %d",&n,&m),n||m){
    82         init();
    83         for(int i = 0; i < m; ++i){
    84             scanf("%d %d",&u,&v);
    85             add(head,u,v);
    86             add(head,v,u);
    87         }
    88         tarjan(1,-1);
    89         for(int i = 1; i <= n; ++i)
    90         for(int j = head[i]; ~j; j = e[j].next){
    91             if(belong[i] != belong[e[j].to])
    92                 add(hd,belong[i],belong[e[j].to]);
    93         }
    94         printf("%d
    ",scc - 1 - d[bfs(bfs(1))]);
    95     }
    96     return 0;
    97 }
    View Code

    很容易想到树的直径就是某一点到两个最长点的和。。。

     1 #pragma comment(linker, "/STACK:102400000,102400000")
     2 #include <iostream>
     3 #include <queue>
     4 #include <cstdio>
     5 #include <cstring>
     6 #include <stack>
     7 using namespace std;
     8 const int maxn = 200010;
     9 struct arc {
    10     int to,next;
    11     arc(int x = 0,int y = -1) {
    12         to = x;
    13         next = y;
    14     }
    15 } e[4000000];
    16 int head[maxn],dfn[maxn],low[maxn],belong[maxn];
    17 int scc,idx,tot,n,m,dp[maxn][2];
    18 bool instack[maxn];
    19 stack<int>stk;
    20 void add(int *head,int u,int v) {
    21     e[tot] = arc(v,head[u]);
    22     head[u] = tot++;
    23 }
    24 void tarjan(int u,int fa) {
    25     dfn[u] = low[u] = ++idx;
    26     instack[u] = true;
    27     stk.push(u);
    28     dp[u][0] = dp[u][1] = 0;
    29     bool flag = true;
    30     for(int i = head[u]; ~i; i = e[i].next) {
    31         if(e[i].to == fa && flag) {
    32             flag = false;
    33             continue;
    34         }
    35         if(!dfn[e[i].to]) {
    36             tarjan(e[i].to,u);
    37             low[u] = min(low[u],low[e[i].to]);
    38             int tmp = dp[e[i].to][1] + (low[e[i].to] > dfn[u]);
    39             if(tmp > dp[u][1]) {
    40                 swap(dp[u][1],dp[u][0]);
    41                 dp[u][1] = tmp;
    42             } else if(tmp > dp[u][0]) dp[u][0] = tmp;
    43         } else if(instack[e[i].to]) low[u] = min(low[u],dfn[e[i].to]);
    44     }
    45     if(low[u] == dfn[u]) {
    46         scc++;
    47         int v;
    48         do {
    49             instack[v = stk.top()] = false;
    50             stk.pop();
    51             belong[v] = scc;
    52         } while(v != u);
    53     }
    54 }
    55 void init() {
    56     for(int i = 0; i < maxn; ++i) {
    57         head[i] = -1;
    58         belong[i] = low[i] = dfn[i] = 0;
    59         instack[i] = false;
    60     }
    61     idx = scc = tot = 0;
    62     while(!stk.empty()) stk.pop();
    63 }
    64 int main() {
    65     int u,v;
    66     while(scanf("%d %d",&n,&m),n||m) {
    67         init();
    68         for(int i = 0; i < m; ++i) {
    69             scanf("%d %d",&u,&v);
    70             add(head,u,v);
    71             add(head,v,u);
    72         }
    73         tarjan(1,-1);
    74         int ans = 0;
    75         for(int i = 1; i <= n; ++i)
    76             ans = max(ans,dp[i][1] + dp[i][0]);
    77         printf("%d
    ",scc - 1 - ans);
    78     }
    79     return 0;
    80 }
    View Code
  • 相关阅读:
    扁鹊见蔡桓公
    月出
    TypeScript 基本类型
    随机漂浮图片广告实例代码
    js实现的随机颜色实例代码
    初识JavaScript 变量, 操作符, 数组
    HTML5的新结构标签
    14款超时尚的HTML5时钟动画
    CSS如何设置div半透明效果
    Google Doodle 2015圣诞版背后的故事与十年圣诞回顾
  • 原文地址:https://www.cnblogs.com/crackpotisback/p/4393923.html
Copyright © 2011-2022 走看看