码迷,mamicode.com
首页 > 其他好文 > 详细

SPOJ Qtree系列 2/7

时间:2018-10-14 13:55:48      阅读:122      评论:0      收藏:0      [点我收藏+]

标签:mes   ons   max   mem   tar   while   struct   for   blank   

Qtree1

树剖裸题

注意把边权移到深度较深的点上,树剖跳的时候不要将LCA的答案统计上就行了

  1 #include<stdio.h>
  2 #include<string.h>
  3 #define MAXN 100001
  4 int read(){
  5     int a = 0;
  6     int f = 0;
  7     char c = getchar();
  8     while(!isdigit(c)){
  9         if(c == -)
 10             f = 1;
 11         c = getchar();
 12     }
 13     while(isdigit(c)){
 14         a = (a << 3) + (a << 1) + (c ^ 0);
 15         c = getchar();
 16     }
 17     return f ? -a : a;
 18 }
 19 
 20 char output[20];
 21 void print(int x){
 22     int dirN = 18;
 23     if(x == 0)
 24         fwrite("0" , sizeof(char) , 1 , stdout);
 25     else{
 26         if(x < 0){
 27             x = -x;
 28             fwrite("-" , sizeof(char) , 1 , stdout);
 29         }
 30         while(x){
 31                output[--dirN] = x % 10 + 48;
 32             x /= 10;
 33         }
 34         fwrite(output + dirN , 1 , strlen(output + dirN) , stdout);
 35     }
 36     fwrite("\n" , 1 , 1 , stdout);
 37 }
 38 
 39 int max(int a , int b){
 40     return a > b ? a : b;
 41 }
 42 
 43 struct node{
 44     int l , r , maxN;
 45 }Tree[MAXN << 2];
 46 struct Edge{
 47     int end , upEd , w;
 48 }Ed[MAXN << 1];
 49 int head[MAXN] , start[MAXN << 1] , size[MAXN] , son[MAXN] , fa[MAXN] , dep[MAXN];
 50 int top[MAXN] , ind[MAXN] , rk[MAXN] , val[MAXN] , N = 0 , cntEd = 0 , ts = 0;
 51 
 52 void addEd(int a , int b , int c){
 53     Ed[++cntEd].end = b;
 54     Ed[cntEd].upEd = head[a];
 55     Ed[cntEd].w = c;
 56     head[a] = cntEd;
 57 }
 58 
 59 void dfs1(int dir , int father , int w){
 60     val[dir] = w;
 61     dep[dir] = dep[fa[dir] = father] + 1;
 62     size[dir] = 1;
 63     int i;
 64     for(i = head[dir] ; i ; i = Ed[i].upEd)
 65         if(!dep[Ed[i].end]){
 66             dfs1(Ed[i].end , dir , Ed[i].w);
 67             size[dir] += size[Ed[i].end];
 68             if(size[son[dir]] < size[Ed[i].end])
 69                 son[dir] = Ed[i].end;
 70         }
 71 }
 72 
 73 void dfs2(int dir , int t){
 74     top[dir] = t;
 75     rk[ind[dir] = ++ts] = dir;
 76     if(!son[dir])
 77         return;
 78     dfs2(son[dir] , t);
 79     int i;
 80     for(i = head[dir] ; i ; i = Ed[i].upEd)
 81         if(Ed[i].end != fa[dir] && Ed[i].end != son[dir])
 82             dfs2(Ed[i].end , Ed[i].end);
 83 }
 84 
 85 void pushup(int dir){
 86     Tree[dir].maxN = max(Tree[dir << 1].maxN , Tree[dir << 1 | 1].maxN);
 87 }
 88 
 89 void init(int dir , int l , int r){
 90     Tree[dir].l = l;
 91     Tree[dir].r = r;
 92     if(l == r)
 93         Tree[dir].maxN = val[rk[l]];
 94     else{
 95         init(dir << 1 , l , l + r >> 1);
 96         init(dir << 1 | 1 , (l + r >> 1) + 1 , r);
 97         pushup(dir);
 98     }
 99 }
100 
101 void change(int dir , int tar , int val){
102     if(Tree[dir].l == Tree[dir].r){
103         Tree[dir].maxN = val;
104         return;
105     }
106     if(Tree[dir].l + Tree[dir].r >> 1 >= tar)
107         change(dir << 1 , tar , val);
108     else
109         change(dir << 1 | 1 , tar , val);
110     pushup(dir);
111 }
112 
113 int findMax(int dir , int l , int r){
114     if(Tree[dir].l >= l && Tree[dir].r <= r)
115         return Tree[dir].maxN;
116     int maxN = 0;
117     if(l <= Tree[dir].l + Tree[dir].r >> 1)
118         maxN = max(maxN , findMax(dir << 1 , l , r));
119     if(r > Tree[dir].l + Tree[dir].r >> 1)
120         maxN = max(maxN , findMax(dir << 1 | 1 , l , r));
121     return maxN;
122 }
123 
124 void work(int x , int y){
125     if(x == y){
126         print(0);
127         return;
128     }
129     int tx = top[x] , ty = top[y] , maxN = -0x7fffffff;
130     while(tx != ty)
131         if(dep[tx] >= dep[ty]){
132             maxN = max(maxN , findMax(1 , ind[tx] , ind[x]));
133             x = fa[tx];
134             tx = top[x];
135         }
136         else{
137             maxN = max(maxN , findMax(1 , ind[ty] , ind[y]));
138             y = fa[ty];
139             ty = top[y];
140         }
141     if(ind[x] < ind[y])
142         maxN = max(maxN , findMax(1 , ind[x] + 1 , ind[y]));
143     if(ind[y] < ind[x])
144         maxN = max(maxN , findMax(1 , ind[y] + 1 , ind[x]));
145     print(maxN);
146 }
147 
148 int cmp(int a , int b){
149     return dep[a] < dep[b] ? ind[b] : ind[a];
150 }
151 
152 char s[10];
153 int main(){
154         N = read();
155         memset(head , 0 , sizeof(head));
156         cntEd = 0;
157         int i;
158         for(i = 1 ; i < N ; i++){
159             start[(i << 1) - 1] = read();
160             start[i << 1] = read();
161             int c = read();
162             addEd(start[(i << 1) - 1] , start[i << 1] , c);
163             addEd(start[i << 1] , start[(i << 1) - 1] , c);
164         }
165         dfs1(1 , 0 , 0);
166         dfs2(1 , 1);
167         init(1 , 1 , N);
168         while(scanf("%s" , s) && s[0] != D){
169             int a = read() , b = read();
170             if(s[0] == Q)
171                 work(a , b);
172             else
173                 change(1 , cmp(start[a << 1] , start[(a << 1) - 1]) , b);
174         }
175     return 0;
176 }

 

Qtree3

树剖裸题+1

将对应白点的叶子节点的值设为INF,黑点的叶子节点的值设为自己的编号,线段树维护$min$即可

  1 #include<bits/stdc++.h>
  2 #define MAXN 100001
  3 using namespace std;
  4 
  5 namespace IO{
  6     const int maxn((1 << 21) + 1);
  7     char ibuf[maxn], *iS, *iT, obuf[maxn], *oS = obuf, *oT = obuf + maxn - 1, c, st[55];
  8     int f, tp;
  9     char Getc() {
 10         return (iS == iT ? (iT = (iS = ibuf) + fread(ibuf, 1, maxn, stdin), (iS == iT ? EOF : *iS++)) : *iS++);
 11     }
 12     void Flush() {
 13         fwrite(obuf, 1, oS - obuf, stdout);
 14         oS = obuf;
 15     }
 16     void Putc(char x) {
 17         *oS++ = x;
 18         if (oS == oT) Flush();
 19     }
 20     template <class Int> void Input(Int &x) {
 21         for (f = 1, c = Getc(); c < 0 || c > 9; c = Getc()) f = c == - ? -1 : 1;
 22         for (x = 0; c <= 9 && c >= 0; c = Getc()) x = (x << 3) + (x << 1) + (c ^ 48);
 23         x *= f;
 24     }
 25     template <class Int> void Print(Int x) {
 26         if (!x) Putc(0);
 27         if (x < 0) Putc(-), x = -x;
 28         while (x) st[++tp] = x % 10 + 0, x /= 10;
 29         while (tp) Putc(st[tp--]);
 30     }
 31     void Getstr(char *s, int &l) {
 32         for (c = Getc(); c < a || c > z; c = Getc());
 33         for (l = 0; c <= z && c >= a; c = Getc()) s[l++] = c;
 34         s[l] = 0;
 35     }
 36     void Putstr(const char *s) {
 37         for (int i = 0, n = strlen(s); i < n; ++i) Putc(s[i]);
 38     }
 39 }
 40 using namespace IO;
 41 
 42 struct node{
 43     int l , r , minN;
 44 }Tree[MAXN << 2];
 45 struct Edge{
 46     int end , upEd;
 47 }Ed[MAXN << 1];
 48 int son[MAXN] , size[MAXN] , fa[MAXN] , dep[MAXN] , head[MAXN];
 49 int top[MAXN] , ind[MAXN] , rk[MAXN] , N , cntEd , ts;
 50 
 51 inline void addEd(int a , int b){
 52     Ed[++cntEd].end = b;
 53     Ed[cntEd].upEd = head[a];
 54     head[a] = cntEd;
 55 }
 56 
 57 void dfs1(int dir , int father){
 58     size[dir] = 1;
 59     dep[dir] = dep[fa[dir] = father] + 1;
 60     for(int i = head[dir] ; i ; i = Ed[i].upEd)
 61         if(!dep[Ed[i].end]){
 62             dfs1(Ed[i].end , dir);
 63             size[dir] += size[Ed[i].end];
 64             if(size[son[dir]] < size[Ed[i].end])
 65                 son[dir] = Ed[i].end;
 66         }
 67 }
 68 
 69 void dfs2(int dir , int t){
 70     top[dir] = t;
 71     rk[ind[dir] = ++ts] = dir;
 72     if(!son[dir])
 73         return;
 74     dfs2(son[dir] , t);
 75     for(int i = head[dir] ; i ; i = Ed[i].upEd)
 76         if(Ed[i].end != son[dir] && Ed[i].end != fa[dir])
 77             dfs2(Ed[i].end , Ed[i].end);
 78 }
 79 
 80 inline int min(int a , int b){
 81     return a < b ? a : b;
 82 }
 83 
 84 void init(int dir , int l , int r){
 85     Tree[dir].l = l;
 86     Tree[dir].r = r;
 87     if(l == r)
 88         Tree[dir].minN = 999999;
 89     else{
 90         init(dir << 1 , l , (l + r) >> 1);
 91         init(dir << 1 | 1 , ((l + r) >> 1) + 1 , r);
 92         Tree[dir].minN = min(Tree[dir << 1].minN , Tree[dir << 1 | 1].minN);
 93     }
 94 }
 95 
 96 void change(int dir , int tar){
 97     if(Tree[dir].l == Tree[dir].r){
 98         Tree[dir].minN = Tree[dir].minN == 999999 ? Tree[dir].l : 999999;
 99         return;
100     }
101     if(tar <= (Tree[dir].l + Tree[dir].r) >> 1)
102         change(dir << 1 , tar);
103     else
104         change(dir << 1 | 1 , tar);
105     Tree[dir].minN = min(Tree[dir << 1].minN , Tree[dir << 1 | 1].minN);
106 }
107 
108 int findMin(int dir , int l , int r){
109     if(Tree[dir].l >= l && Tree[dir].r <= r)
110         return Tree[dir].minN;
111     int minN;
112     if(l <= (Tree[dir].l + Tree[dir].r) >> 1){
113         minN = findMin(dir << 1 , l , r);
114         if(minN != 999999)
115             return minN;
116     }
117     if(r > (Tree[dir].l + Tree[dir].r) >> 1)
118         return findMin(dir << 1 | 1 , l , r);
119     return 999999;
120 }
121 
122 inline int work(int tar){
123     int minN = 999999;
124     while(top[tar] != 1){
125         minN = min(minN , findMin(1 , ind[top[tar]] , ind[tar]));
126         tar = fa[top[tar]];
127     }
128     minN = min(minN , findMin(1 , 1 , ind[tar]));
129     return minN == 999999 ? -1 : rk[minN];
130 }
131 
132 int main(){
133     int N , M;
134     Input(N);
135     Input(M);
136     for(int i = 1 ; i < N ; i++){
137         int a , b;
138         Input(a);
139         Input(b);
140         addEd(a , b);
141         addEd(b , a);
142     }
143     dfs1(1 , 0);
144     dfs2(1 , 1);
145     init(1 , 1 , N);
146     while(M--){
147         int a;
148         Input(a);
149         if(a == 0){
150             Input(a);
151             change(1 , ind[a]);
152         }
153         else{
154             Input(a);
155             Print(work(a));
156             Putc(\n);
157         }
158     }
159     Flush();
160     return 0;
161 }

 

SPOJ Qtree系列 2/7

标签:mes   ons   max   mem   tar   while   struct   for   blank   

原文地址:https://www.cnblogs.com/Itst/p/9785526.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!