zoukankan      html  css  js  c++  java
  • 1036: [ZJOI2008]树的统计Count

    Description

    一棵树上有n个节点,编号分别为1到n,每个节点都有一个权值w。我们将以下面的形式来要求你对这棵树完成一些操作: I. CHANGE u t : 把结点u的权值改为t II. QMAX u v: 询问从点u到点v的路径上的节点的最大权值 III. QSUM u v: 询问从点u到点v的路径上的节点的权值和 注意:从点u到点v的路径上的节点包括u和v本身
    Input

    输入的第一行为一个整数n,表示节点的个数。接下来n – 1行,每行2个整数a和b,表示节点a和节点b之间有一条边相连。接下来n行,每行一个整数,第i行的整数wi表示节点i的权值。接下来1行,为一个整数q,表示操作的总数。接下来q行,每行一个操作,以“CHANGE u t”或者“QMAX u v”或者“QSUM u v”的形式给出。 对于100%的数据,保证1<=n<=30000,0<=q<=200000;中途操作中保证每个节点的权值w在-30000到30000之间。
    Output

    对于每个“QMAX”或者“QSUM”的操作,每行输出一个整数表示要求输出的结果。
    Sample Input
    4
    1 2
    2 3
    4 1
    4 2 1 3
    12
    QMAX 3 4
    QMAX 3 3
    QMAX 3 2
    QMAX 2 3
    QSUM 3 4
    QSUM 2 1
    CHANGE 1 5
    QMAX 3 4
    CHANGE 3 6
    QMAX 3 4
    QMAX 2 4
    QSUM 3 4
    Sample Output
    4
    1
    2
    2
    10
    6
    5
    6
    5
    16

    裸树链剖分,我就不多说了,附入门教程

      1 const
      2     maxn=30010;
      3 type
      4     node=record
      5       son:array[0..1]of longint;
      6       sum,max,left,right,mid:longint;
      7     end;
      8 var
      9     n,m,num,tot,xx,ll,rr,goal:longint;
     10     tree:array[0..maxn*2]of node;
     11     first,fa,dep,son,size,w,top,root:array[0..maxn]of longint;
     12     next,last:array[0..maxn*2]of longint;
     13 
     14 procedure insert(x,y:longint);
     15 begin
     16     inc(num);
     17     last[num]:=y;
     18     next[num]:=first[x];
     19     first[x]:=num;
     20 end;
     21 
     22 procedure dfs1(x,d,f:longint);
     23 var
     24     i:longint;
     25 begin
     26     dep[x]:=d;
     27     fa[x]:=f;
     28     size[x]:=1;
     29     i:=first[x];
     30     while i<>0 do
     31       begin
     32         if last[i]<>f then
     33         begin
     34           dfs1(last[i],d+1,x);
     35           if size[last[i]]>size[son[x]] then son[x]:=last[i];
     36           inc(size[x],size[last[i]]);
     37         end;
     38         i:=next[i];
     39       end;
     40 end;
     41 
     42 procedure build(l,r:longint);
     43 var
     44     now:longint;
     45 begin
     46     inc(tot);
     47     now:=tot; 
     48     with tree[now] do
     49       begin
     50         left:=l;
     51         right:=r;
     52         if l=r then exit;
     53         mid:=(l+r)>>1;
     54         son[0]:=tot+1;
     55         build(l,mid);
     56         son[1]:=tot+1;
     57         build(mid+1,r);
     58       end;
     59 end;
     60 
     61 procedure dfs2(x,t,ww:longint);
     62 var
     63     i:longint;
     64 begin
     65     w[x]:=ww;
     66     top[x]:=t;
     67     if son[x]=0 then
     68       begin
     69         root[x]:=tot+1;
     70         build(1,ww);
     71         exit;
     72       end
     73     else
     74       begin
     75         dfs2(son[x],t,ww+1);
     76         root[x]:=root[son[x]];
     77       end;
     78     i:=first[x];
     79     while i<>0 do
     80       begin
     81         if (last[i]<>fa[x]) and (last[i]<>son[x]) then dfs2(last[i],last[i],1);
     82         i:=next[i];
     83       end;
     84 end;
     85 
     86 procedure change(now:longint);
     87 begin
     88     with tree[now] do
     89       begin
     90         if left=right then
     91         begin
     92           sum:=goal;
     93           max:=goal;
     94           exit;
     95         end;
     96         if xx<=mid then change(son[0])
     97         else change(son[1]);
     98         if tree[son[0]].max>tree[son[1]].max then max:=tree[son[0]].max
     99         else max:=tree[son[1]].max;
    100         sum:=tree[son[0]].sum+tree[son[1]].sum;
    101       end;
    102 end;
    103 
    104 function getsum(now:longint):longint;
    105 begin
    106     with tree[now] do
    107       begin
    108         if (ll<=left) and (rr>=right) then exit(sum);
    109         if rr<=mid then exit(getsum(son[0]));
    110         if ll>mid then exit(getsum(son[1]));
    111         exit(getsum(son[0])+getsum(son[1]));
    112       end;
    113 end;
    114 
    115 function getmax(now:longint):longint;
    116 var
    117     s:longint;
    118 begin
    119     with tree[now] do
    120       begin
    121         if (ll<=left) and (rr>=right) then exit(max);
    122         if rr<=mid then exit(getmax(son[0]));
    123         if ll>mid then exit(getmax(son[1]));
    124         getmax:=getmax(son[0]);
    125         s:=getmax(son[1]);
    126         if s>getmax then getmax:=s;
    127       end;
    128 end;
    129 
    130 procedure init;
    131 var
    132     i,x,y:longint;
    133 begin
    134     read(n);
    135     for i:=1 to n-1 do
    136       begin
    137         read(x,y);
    138         insert(x,y);
    139         insert(y,x);
    140       end;
    141     dfs1(1,1,0);
    142     dfs2(1,1,1);
    143     for i:=1 to n do
    144       begin
    145         read(goal);
    146         xx:=w[i];
    147         change(root[i]);
    148       end;
    149 end;
    150 
    151 procedure work;
    152 var
    153     i,ans,s,x,y:longint;
    154     s1,s2:char;
    155 begin
    156     read(m);
    157     for i:=1 to m do
    158       begin
    159         read(s2);
    160         while s2<>' ' do
    161           begin
    162             s1:=s2;
    163             read(s2);
    164           end;
    165         read(x,y);
    166         case s1 of
    167           'E':begin
    168             goal:=y;
    169             xx:=w[x];
    170             change(root[x]);
    171           end;
    172           'X':begin
    173             ans:=-300000;
    174             while top[x]<>top[y] do
    175               begin
    176                 if dep[top[x]]<dep[top[y]] then
    177                 begin
    178                   s:=x;x:=y;y:=s;
    179                 end;
    180                 ll:=1;
    181                 rr:=w[x];
    182                 s:=getmax(root[x]);
    183                 if s>ans then ans:=s;
    184                 x:=fa[top[x]];
    185               end;
    186             if dep[x]<dep[y] then
    187             begin
    188               s:=x;x:=y;y:=s;
    189             end;
    190             ll:=w[y];
    191             rr:=w[x];
    192             s:=getmax(root[x]);
    193             if s>ans then ans:=s;
    194             writeln(ans);
    195           end;
    196           'M':begin
    197             ans:=0;
    198             while top[x]<>top[y] do
    199               begin
    200                 if dep[top[x]]<dep[top[y]] then
    201                 begin
    202                   s:=x;x:=y;y:=s;
    203                 end;
    204                 ll:=1;
    205                 rr:=w[x];
    206                 inc(ans,getsum(root[x]));
    207                 x:=fa[top[x]];
    208               end;
    209             if dep[x]<dep[y] then
    210             begin
    211               s:=x;x:=y;y:=s;
    212             end;
    213             ll:=w[y];
    214             rr:=w[x];
    215             inc(ans,getsum(root[x]));
    216             writeln(ans);
    217           end;
    218         end;
    219       end;
    220 end;
    221 
    222 begin
    223     init;
    224     work;
    225 end.
    View Code
  • 相关阅读:
    Atitit.随时间变色特效 ---包厢管理系统的规划
    Atitit.request http乱码的设计防止 检测与解决最近实践p825 attilax总结.doc
    Atitit.request http乱码的设计防止 检测与解决最近实践p825 attilax总结.doc
    atitit.薄伽梵歌overview  attilax 读后感
    Atitit。 《吠陀》 《梨俱吠陀》overview 经读后感  是印度上古时期一些文献的总称
    Atitit。 《吠陀》 《梨俱吠陀》overview 经读后感  是印度上古时期一些文献的总称
    atitit.薄伽梵歌overview  attilax 读后感
    Atitit 《摩奴法典》overivew 读后感 不是由国王 颁布的,而是 僧侣编制
    Atitit 《摩奴法典》overivew 读后感 不是由国王 颁布的,而是 僧侣编制
    Atitit.执行cli cmd的原理与调试
  • 原文地址:https://www.cnblogs.com/Randolph87/p/3648820.html
Copyright © 2011-2022 走看看