Advertisement
mickypinata

CUBE-T190: Supernova

Nov 22nd, 2021
732
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 2.52 KB | None | 0 0
  1. #include <bits/stdc++.h>
  2. using namespace std;
  3.  
  4. typedef long long lli;
  5. typedef pair<int, int> pii;
  6.  
  7. const int N = 1e5 + 5;
  8.  
  9. vector<pii> adj[N];
  10. vector<int> cAdj[N];
  11. pii edges[N];
  12. int disc[N], low[N], isBridge[N], cVertex[N], dens[N], subTree[N], par[N];
  13. lli ans[N];
  14. bool visited[N];
  15.  
  16. int discCnt = 0;
  17. void DFSBridge(int u, int pEdge){
  18.     disc[u] = ++discCnt;
  19.     low[u] = disc[u];
  20.     visited[u] = true;
  21.     for(pii nxt : adj[u]){
  22.         int v = nxt.first;
  23.         int i = nxt.second;
  24.         if(i == pEdge){
  25.             continue;
  26.         }
  27.         if(visited[v]){
  28.             low[u] = min(low[u], disc[v]);
  29.         } else {
  30.             DFSBridge(v, i);
  31.             low[u] = min(low[u], low[v]);
  32.             if(low[v] > disc[u]){
  33.                 isBridge[i] = true;
  34.             }
  35.         }
  36.     }
  37. }
  38.  
  39. void DFSConnect(int u, int idx){
  40.     cVertex[u] = idx;
  41.     ++dens[idx];
  42.     visited[u] = true;
  43.     for(pii nxt : adj[u]){
  44.         int v = nxt.first;
  45.         int i = nxt.second;
  46.         if(!visited[v] && !isBridge[i]){
  47.             DFSConnect(v, idx);
  48.         }
  49.     }
  50. }
  51.  
  52. void DFS(int u, int p){
  53.     par[u] = p;
  54.     int cnt = dens[u];
  55.     for(int v : cAdj[u]){
  56.         if(v == p){
  57.             continue;
  58.         }
  59.         DFS(v, u);
  60.         cnt += subTree[v];
  61.     }
  62.     subTree[u] = cnt;
  63. }
  64.  
  65. int main(){
  66.  
  67.     int nVertex, nEdge;
  68.     scanf("%d%d", &nVertex, &nEdge);
  69.     for(int i = 1; i <= nEdge; ++i){
  70.         int u, v;
  71.         scanf("%d%d", &u, &v);
  72.         adj[u].emplace_back(v, i);
  73.         adj[v].emplace_back(u, i);
  74.         edges[i] = pii(u, v);
  75.     }
  76.     DFSBridge(1, 0);
  77.     for(int u = 1; u <= nVertex; ++u){
  78.         visited[u] = false;
  79.     }
  80.     int idx = 0;
  81.     for(int u = 1; u <= nVertex; ++u){
  82.         if(!visited[u]){
  83.             DFSConnect(u, ++idx);
  84.         }
  85.     }
  86.     for(int i = 1; i <= nEdge; ++i){
  87.         if(isBridge[i]){
  88.             int u = cVertex[edges[i].first];
  89.             int v = cVertex[edges[i].second];
  90.             cAdj[u].push_back(v);
  91.             cAdj[v].push_back(u);
  92.         }
  93.     }
  94.     DFS(1, 0);
  95.     for(int i = 1; i <= nEdge; ++i){
  96.         if(isBridge[i]){
  97.             int u = cVertex[edges[i].first];
  98.             int v = cVertex[edges[i].second];
  99.             if(par[u] == v){
  100.                 swap(u, v);
  101.             }
  102.             ans[i] = (lli)subTree[v] * (nVertex - subTree[v]);
  103.         } else {
  104.             ans[i] = 0;
  105.         }
  106.     }
  107.     for(int i = 1; i <= nEdge; ++i){
  108.         cout << ans[i] << ' ';
  109.     }
  110.  
  111.     return 0;
  112. }
  113.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement