http://www.lydsy.com/JudgeOnline/problem.php?id=2631
支持
1.路径整体+c
2.路径整体*c
3.断边连边
4.路径和查询
用这道题来整理一份LCT模板
{$M 100000000}
const
maxn=100050;
mmod=51061;
var
w:array[0..3*maxn,1..2]of longint;
son:array[0..maxn,1..2]of longint;
fa,rev,size,sum,val,add,mal:array[0..maxn]of longint;
i,j,k:longint;
n,m,a,b,c,d,len,tt:longint;
cha:char;
procedure swap(var a,b:longint);
var c:longint;
begin c:=a; a:=b; b:=c; end;
procedure init(a,b:longint);
begin
w[len,1]:=b;
if w[a,2]=0 then w[a,2]:=len else w[w[a,1],2]:=len;
w[a,1]:=len; inc(len);
end;
procedure dfs(a:longint);
var tt:longint;
begin
tt:=w[a,2]; size[a]:=1; sum[a]:=1; val[a]:=1; add[a]:=0; mal[a]:=1; son[a,1]:=0; son[a,2]:=0; rev[a]:=0;
while tt<>0 do
begin
if w[tt,1]<>fa[a] then begin fa[w[tt,1]]:=a; dfs(w[tt,1]); end;
tt:=w[tt,2];
end;
end;
procedure update(a:longint);
begin
if a=0 then exit;
size[a]:=size[son[a,1]]+size[son[a,2]]+1;
sum[a]:=(sum[son[a,1]]+sum[son[a,2]]+val[a])mod mmod;
end;
function isroot(a:longint):longint;
begin if (son[fa[a],1]<>a)and(son[fa[a],2]<>a) then exit(1) else exit(0); end;
procedure addd(a,b:longint);
begin
if a=0 then exit;
val[a]:=(val[a]+b)mod mmod;
sum[a]:=(sum[a]+int64(b)*size[a])mod mmod;
add[a]:=(add[a]+b)mod mmod;
end;
procedure mall(a:longint;b:int64);
begin
if a=0 then exit;
val[a]:=(b*val[a])mod mmod;
sum[a]:=(b*sum[a])mod mmod;
mal[a]:=(b*mal[a])mod mmod;
add[a]:=(b*add[a])mod mmod;
end;
procedure pushdown(a:longint);
begin
if a=0 then exit;
if mal[a]<>1
then
begin
mall(son[a,1],int64(mal[a]));
mall(son[a,2],int64(mal[a]));
mal[a]:=1;
end;
if add[a]<>0
then
begin
addd(son[a,1],add[a]);
addd(son[a,2],add[a]);
add[a]:=0;
end;
if rev[a]=1
then
begin
swap(son[a,1],son[a,2]);
if son[a,1]<>0 then rev[son[a,1]]:=rev[son[a,1]] xor 1;
if son[a,2]<>0 then rev[son[a,2]]:=rev[son[a,2]] xor 1;
rev[a]:=rev[a] xor 1;
end;
end;
procedure rotate(a,kind:longint);
var b,unkind:longint;
begin
b:=fa[a]; unkind:=kind xor 3;
if son[fa[b],1]=b then son[fa[b],1]:=a else
if son[fa[b],2]=b then son[fa[b],2]:=a;
fa[a]:=fa[b];
son[b,kind]:=son[a,unkind]; fa[son[a,unkind]]:=b; son[a,unkind]:=b;
fa[b]:=a;
update(b); update(a);
end;
procedure splay(a:longint);
var b,kind,unkind:longint;
begin
pushdown(a);
while isroot(a)=0 do
begin
b:=fa[a]; pushdown(fa[b]); pushdown(b); pushdown(a);
if son[b,1]=a then kind:=1 else kind:=2; unkind:=kind xor 3;
if isroot(b)=1 then rotate(a,kind)
else
if son[fa[b],kind]=b
then begin rotate(b,kind); rotate(a,kind); end
else begin rotate(a,kind); rotate(a,unkind); end;
end;
end;
procedure access(a:longint);
var b:longint;
begin
splay(a); son[a,2]:=0; update(a);
while fa[a]<>0 do
begin
b:=fa[a];
splay(b);
son[b,2]:=a;
update(b);
splay(a);
end;
end;
procedure makeroot(a:longint);
begin
access(a);
splay(a);
rev[a]:=rev[a] xor 1;
pushdown(a);
end;
procedure link(a,b:longint);
begin
makeroot(a);
fa[a]:=b;
end;
procedure cut(a,b:longint);
begin
makeroot(a);
access(b);
son[b,1]:=0;
fa[a]:=0;
update(b);
end;
procedure work1(a,b,c:longint);
begin
makeroot(a);
access(b);
addd(b,c);
end;
procedure work2(a,b,c,d:longint);
begin
cut(a,b);
link(c,d);
end;
procedure work3(a,b,c:longint);
begin
makeroot(a);
access(b);
mall(b,int64(c));
end;
procedure work4(a,b:longint);
begin
makeroot(a);
access(b);
writeln(sum[b]);
end;
begin
readln(n,m); len:=n+1;
for i:=1 to n-1 do
begin
readln(a,b);
init(a,b); init(b,a);
end;
fa[1]:=0;
dfs(1); tt:=0;
for i:=1 to m do
begin
read(cha);
case cha of
'+':begin readln(a,b,c); work1(a,b,c); end;
'-':begin readln(a,b,c,d); work2(a,b,c,d); end;
'*':begin readln(a,b,c); work3(a,b,c); end;
'/':begin readln(a,b); work4(a,b); end;
end;
end;
end.