Spoj-qtree-tree link splitting (edge partitioning)

Source: Internet
Author: User
Tags rounds

[Preface] ttvtt asked me to WHL and then ...... After 5 rounds of WA, 6 rounds of RE, and 3 rounds of TLE, I finally broke down with this question.

A tree provides an edge weight. There are two operations: change the value of an edge and find the maximum edge weight from path a to path B.

[Click it] This is a good training question for tree link splitting and edge partitioning. However, the data seems abnormal and easy to look like TLE. Actually, I am also in Phuket.

[Idea]: For a tree, each node (except the root node) has only one father. For each edge, the node that is the son is used to record the edge weight. This is generally the case. When TVT is then queried, note that the depth of the first node of the chain is compared with that of the vertex splitting, because the edge splitting is different from that of the vertex splitting, deep points are connected to their parent nodes. Therefore, if we compare the bottom nodes, when we come to the LCA, we will move up to an unnecessary node, an error occurs.

[Conclusion]: map nodes are used to correspond to edges, but TLE is used. Then pre and fun1 are used to correspond to the relations between input vertices and input nodes, use tree and fun2 to correspond to the numbered node and number. That's enough.

The AC code (420 ms ):

[Is the data on Buji island weak? I used it for ms. It seems that some chicory products have used 2.6s _ (: chicory "∠ )_]

  1 #include <iostream>  2 #include <cstdio>  3 #include <cstring>  4 #include <climits>  5 using namespace std;  6 int const maxn = 10009;  7 int pre[maxn], n, edge, cnt, fa[maxn], deep[maxn], num[maxn], son[maxn], tree[maxn], fun1[maxn], fun2[maxn];  8 int to[maxn<<1], next[maxn<<1], head[maxn], top[maxn], seq[maxn<<1], cost[maxn];  9 void add(int u, int v, int num) 10 { 11     to[edge] = v; 12     next[edge] = head[u]; 13     seq[edge] = num; 14     head[u] = edge++; 15 } 16 void init() 17 { 18     scanf("%d", &n); 19     memset(head, -1, sizeof(head)); 20     memset(son, -1, sizeof(son)); 21     edge = cnt = 0; 22     for(int i = 1; i < n; i++) { 23         int a, b; scanf("%d%d%d", &a, &b, &cost[i]); 24         add(a, b, i); add(b, a, i); 25     } 26     fa[1] = deep[1] = tree[1] = 1; 27 } 28 void dfs1(int u) 29 { 30     num[u] = 1; 31     for(int e = head[u]; ~e; e = next[e]) { 32         int too = to[e]; 33         if(fa[u] != too) { 34             pre[seq[e]] = too;      //把输入的边和较深的节点对应起来 35             fun1[too] = seq[e];     //存节点对应的边 36             deep[too] = deep[u]+1; 37             fa[too] = u; 38             dfs1(too); num[u] += num[too]; 39             if(son[u] == -1||num[son[u]] < num[too]) son[u] = too; 40         } 41     } 42 } 43 void dfs2(int u, int lead) 44 { 45     top[u] = lead; 46     if(u != 1) tree[u] = ++cnt, fun2[cnt] = u; //剖分的编号一一对应 47     if(son[u] == -1) return; 48     dfs2(son[u], lead); 49     for(int e = head[u]; ~e; e = next[e]) { 50         int too = to[e]; 51         if(fa[u] != too && son[u] != too) dfs2(too, too); 52     } 53 } 54 #define lson l, m, rt<<1 55 #define rson m+1, r, rt<<1|1 56 int sgt[maxn<<2] = {INT_MIN}; 57 void push_up(int rt) 58 { 59     sgt[rt] = max(sgt[rt<<1], sgt[rt<<1|1]); 60 } 61 void build(int l, int r, int rt) 62 { 63     if(l == r) { 64         int pos = fun1[fun2[l]]; 65         sgt[rt] = cost[pos]; return; 66     } 67     int m = (l+r)>>1; 68     build(lson); build(rson); 69     push_up(rt); 70 } 71 void change(int l, int r, int rt, int pos, int val) 72 { 73     if(l == r) { sgt[rt] = val; return; } 74     int m = (l+r)>>1; 75     if(pos <= m) change(lson, pos, val); 76     if(m < pos) change(rson, pos, val); 77     push_up(rt); 78 } 79 int query(int l, int r, int rt, int L, int R) 80 { 81     if(L <= l && r <= R) return sgt[rt]; 82     int m = (l+r)>>1; 83     int a, b; a = b = INT_MIN; 84     if(L <= m) a = query(lson, L, R); 85     if(m < R) b = query(rson, L, R); 86     return max(a, b); 87 } 88 int answer(int a, int b) 89 { 90     if(a == b) return 0; 91     int ans = INT_MIN; 92     while(top[a] != top[b]) { 93         if(deep[top[a]] < deep[top[b]]) swap(a, b); 94         ans = max(ans, query(1, n-1, 1, tree[top[a]], tree[a])); 95         a = fa[top[a]]; 96     } 97     if(deep[a] > deep[b]) swap(a, b); 98     if(a != b) ans = max(ans, query(1, n-1, 1, tree[son[a]], tree[b])); 99     return ans;100 }101 void work()102 {103     init();104     dfs1(1); dfs2(1, 1); build(1, n-1, 1);105     char s[20];106     while(scanf("%s", s) && s[0] != ‘D‘) {107         int a, b; scanf("%d%d", &a, &b);108         if(s[0] == ‘C‘) {109             change(1, n-1, 1, tree[pre[a]], b);110         }111         else {112             printf("%d\n", answer(a, b));113         }114     }115 }116 int main()117 {118     int t; cin>>t;119     while(t--) work();120     return 0;121 }
View code

 

Spoj-qtree-tree link splitting (edge partitioning)

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.