zoukankan      html  css  js  c++  java
  • HDU5296 Annoying problem(LCA)

      1 //#pragma comment(linker, "/STACK:1677721600")
      2 #include <map>
      3 #include <set>
      4 #include <stack>
      5 #include <queue>
      6 #include <cmath>
      7 #include <ctime>
      8 #include <vector>
      9 #include <cstdio>
     10 #include <cctype>
     11 #include <cstring>
     12 #include <cstdlib>
     13 #include <iostream>
     14 #include <algorithm>
     15 using namespace std;
     16 #define INF 0x3f3f3f3f
     17 #define inf (-((LL)1<<40))
     18 #define lson k<<1, L, (L + R)>>1
     19 #define rson k<<1|1,  ((L + R)>>1) + 1, R
     20 #define mem0(a) memset(a,0,sizeof(a))
     21 #define mem1(a) memset(a,-1,sizeof(a))
     22 #define mem(a, b) memset(a, b, sizeof(a))
     23 #define FIN freopen("in.txt", "r", stdin)
     24 #define FOUT freopen("out.txt", "w", stdout)
     25 #define rep(i, a, b) for(int i = (a); i <= (b); i ++)
     26 #define dec(i, a, b) for(int i = (a); i >= (b); i --)
     27 
     28 template<class T> T MAX(T a, T b) { return a > b ? a : b; }
     29 template<class T> T MIN(T a, T b) { return a < b ? a : b; }
     30 template<class T> T GCD(T a, T b) { return b ? GCD(b, a%b) : a; }
     31 template<class T> T LCM(T a, T b) { return a / GCD(a,b) * b;    }
     32 
     33 //typedef __int64 LL;
     34 typedef long long LL;
     35 const int MAXN = 100000 + 100;
     36 const int MAXM = 2000000 + 100;
     37 const double eps = 1e-8;
     38 LL MOD = 1000000007;
     39 
     40 struct Edge {
     41     int v, w;
     42     Edge(int _v = 0, int _w = 0) {
     43         v = _v; w = _w;
     44     }
     45 };
     46 
     47 struct LCA {
     48     int idx[MAXN << 1];
     49     int dep[MAXN << 1];
     50     int dp[MAXN << 1][20];
     51     int K[MAXN << 1];
     52     int node_cnt;
     53     vector<Edge>G[MAXN];
     54     int P[MAXN];
     55 
     56     int dis[MAXN];
     57 
     58     void init(int n) {
     59         mem0(dep); mem0(K);
     60         node_cnt = 0;
     61         rep (i, 0, n) G[i].clear();
     62     }
     63     void add_edge(int u, int v, int w) {
     64         G[u].push_back(Edge(v, w));
     65         G[v].push_back(Edge(u, w));
     66     }
     67     void dfs(int u, int fa, int height, int dist) {
     68         idx[++node_cnt] = u;
     69         dep[node_cnt] = height;
     70         P[u] = node_cnt;
     71         dis[u] = dist;
     72         int sz = G[u].size();
     73         rep (i, 0, sz - 1) {
     74             int v = G[u][i].v;
     75             if(v == fa) continue;
     76             dfs(v, u, height + 1, dist + G[u][i].w);
     77             idx[++node_cnt] = u;
     78             dep[node_cnt] = height;
     79         }
     80     }
     81     void init_st_table() {
     82         dfs(1, -1, 0, 0);
     83 
     84         int n = node_cnt;
     85         rep (i, 1, n) {
     86             dp[i][0] = i;
     87             while((1 << (K[i] + 1)) <= i) K[i] ++;
     88         }
     89         for(int j = 1; (1 << j) <= n; j ++) {
     90             for(int i = 1; i + (1 << j) - 1 <= n; i ++) {
     91                 int l_pos = dp[i][j - 1], r_pos = dp[i + (1 << (j - 1))][j - 1];
     92                 dp[i][j] = dep[l_pos] < dep[r_pos] ? l_pos : r_pos;
     93             }
     94         }
     95     }
     96     int rmq_query(int L, int R) {
     97         if(L > R) swap(L, R);
     98         int len = R - L + 1, k = K[len];
     99         return dep[dp[L][k]] < dep[dp[R - (1 << k) + 1][k]] ? dp[L][k] : dp[R - (1 << k) + 1][k];
    100     }
    101     int lca_query(int u, int v) {
    102         int id = rmq_query(P[u], P[v]);
    103         return idx[id];
    104     }
    105 }lca;
    106 
    107 struct SegTree  {
    108     int s[MAXN << 3];
    109     void update(int k, int L, int R, int p, int v) {
    110         if(L == R) { s[k] = v; return ; }
    111         if(((L + R) >> 1) >= p)  update(lson, p, v);
    112         else update(rson, p, v);
    113         s[k] = s[k << 1] + s[k << 1 | 1];
    114     }
    115     int query_sum(int k, int L, int R, int p) {
    116         if(R <= p) return s[k];
    117         if( ((L + R) >> 1) >= p ) return query_sum(lson, p);
    118         return s[k << 1] + query_sum(rson, p);
    119     }
    120     int query_pos(int k, int L, int R, int x) {
    121         if(L == R) return L;
    122         if(s[k << 1] >= x) return query_pos(lson, x);
    123         return query_pos(rson, x - s[k << 1]);
    124     }
    125 }st;
    126 
    127 int t, n, m, cas = 0;
    128 int u, v, w;
    129 bool vis[MAXN << 1];
    130 
    131 int main()
    132 {
    133 //    FIN;
    134     cin >> t;
    135     while(t--) {
    136         scanf("%d %d", &n, &m);
    137         lca.init(n);
    138         rep (i, 2, n) {
    139             scanf("%d %d %d", &u, &v, &w);
    140             lca.add_edge(u, v, w);
    141         }
    142         lca.init_st_table();
    143 
    144         mem0(st.s);
    145         mem0(vis);
    146         int ans = 0;
    147         printf("Case #%d:
    ", ++cas);
    148         while(m --) {
    149             scanf("%d %d", &u, &v);
    150             if( (u == 1 && !vis[v]) || (u == 2 && vis[v]) ) {
    151                 vis[v] = !vis[v];
    152                 if(u == 2) st.update(1, 1, lca.node_cnt, lca.P[v], 0);
    153                 if( st.s[1] ) {
    154                     int x, y;
    155                     int sum = st.query_sum(1, 1, lca.node_cnt, lca.P[v]);
    156                     if( !sum || sum == st.s[1] ) x = 1, y = st.s[1];
    157                     else x = sum, y = sum + 1;
    158                     x = lca.idx[st.query_pos(1, 1, lca.node_cnt, x)];
    159                     y = lca.idx[st.query_pos(1, 1, lca.node_cnt, y)];
    160                     int xv = lca.lca_query(x, v);
    161                     int yv = lca.lca_query(y, v);
    162                     int xy = lca.lca_query(x, y);
    163                     ans += (u == 1 ? 1 : -1) * (lca.dis[v] - lca.dis[xv] - lca.dis[yv] + lca.dis[xy]);
    164                 }
    165                 else ans = 0;
    166                 if(u == 1) st.update(1, 1, lca.node_cnt, lca.P[v], 1);
    167             }
    168             printf("%d
    ", ans);
    169         }
    170     }
    171     return 0;
    172 }
  • 相关阅读:
    一个不错的谈架构的链接
    监控报警平台设计思路
    从数据库到NoSQL思路整理
    大数据流式计算:关键技术及系统实例
    接口和类
    学习的逻辑
    [kuangbin带你飞]专题五 并查集 J
    [kuangbin带你飞]专题五 并查集 E
    [kuangbin带你飞]专题五 并查集 D
    [kuangbin带你飞]专题五 并查集 C
  • 原文地址:https://www.cnblogs.com/gj-Acit/p/4671778.html
Copyright © 2011-2022 走看看