题解:

树剖,线段树维护区间颜色段数

记录两端点的颜色,做到O(1)合并

问题:

  非递归建树实现

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
const int maxn=; int n,m;
int incolor[maxn]; int cntedge;
int head[maxn];
int to[maxn<<],nex[maxn<<];
int addedge(int x,int y){
nex[++cntedge]=head[x];
to[cntedge]=y;
head[x]=cntedge;
} int father[maxn],depth[maxn],siz[maxn];
int heavyson[maxn],top[maxn],idx[maxn],ref[maxn]; int dfs1(int now,int fa){
father[now]=fa;
depth[now]=depth[fa]+;
siz[now]=;
for(int i=head[now];i;i=nex[i]){
if(to[i]==fa)continue;
dfs1(to[i],now);
siz[now]+=siz[to[i]];
if(siz[to[i]]>siz[heavyson[now]]){
heavyson[now]=to[i];
}
}
}
int temp;
int dfs2(int now,int toppoint){
top[now]=toppoint;
idx[now]=(++temp);
ref[temp]=now;
if(!heavyson[now])return ;
dfs2(heavyson[now],toppoint);
for(int i=head[now];i;i=nex[i]){
if(to[i]==father[now])continue;
if(to[i]==heavyson[now])continue;
dfs2(to[i],to[i]);
}
} struct SegmentTree{
int l,r;
int lcolor,rcolor;
int setcolor,sum;
}tree[maxn<<];
int pushup(int now){
tree[now].lcolor=tree[now<<].lcolor;
tree[now].rcolor=tree[now<<|].rcolor;
if(tree[now<<].rcolor==tree[now<<|].lcolor){
tree[now].sum=tree[now<<].sum+tree[now<<|].sum-;
}else{
tree[now].sum=tree[now<<].sum+tree[now<<|].sum;
}
}
int pushdown(int now){
if(tree[now].setcolor!=-){
tree[now<<].setcolor=tree[now<<].lcolor=tree[now<<].rcolor=tree[now].setcolor;
tree[now<<|].setcolor=tree[now<<|].lcolor=tree[now<<|].rcolor=tree[now].setcolor;
tree[now<<].sum=tree[now<<|].sum=;
tree[now].setcolor=-;
}
} int Build(int now,int l,int r){
tree[now].l=l;tree[now].r=r;
tree[now].setcolor=-;
if(l==r){
tree[now].lcolor=tree[now].rcolor=incolor[ref[l]];
tree[now].sum=;
return ;
}
int mid=(l+r)>>;
Build(now<<,l,mid);
Build(now<<|,mid+,r);
pushup(now);
} int Updata(int now,int ll,int rr,int x){
if(tree[now].l>=ll&&tree[now].r<=rr){
tree[now].setcolor=tree[now].lcolor=tree[now].rcolor=x;
tree[now].sum=;
return ;
}
int mid=(tree[now].l+tree[now].r)>>;
pushdown(now);
if(ll<=mid)Updata(now<<,ll,rr,x);
if(rr>mid)Updata(now<<|,ll,rr,x);
pushup(now);
} int Querysum(int now,int ll,int rr){
if(tree[now].l>=ll&&tree[now].r<=rr){
return tree[now].sum;
}
int mid=(tree[now].l+tree[now].r)>>;
pushdown(now);
if(rr<=mid)return Querysum(now<<,ll,rr);
else if(ll>mid)return Querysum(now<<|,ll,rr);
else if(tree[now<<].rcolor==tree[now<<|].lcolor)return Querysum(now<<,ll,rr)+Querysum(now<<|,ll,rr)-;
else return Querysum(now<<,ll,rr)+Querysum(now<<|,ll,rr);
} int Querycolor(int now,int p){
if(tree[now].l==tree[now].r){
return tree[now].lcolor;
}
int mid=(tree[now].l+tree[now].r)>>;
pushdown(now);
if(p<=mid)return Querycolor(now<<,p);
else return Querycolor(now<<|,p);
} int Change(int u,int v,int x){
int tu=top[u];
int tv=top[v];
while(tu!=tv){
if(depth[tu]<depth[tv]){
swap(tu,tv);swap(u,v);
}
Updata(,idx[tu],idx[u],x);
u=father[tu];tu=top[u];
}
if(depth[u]>depth[v])swap(u,v);
Updata(,idx[u],idx[v],x);
} int Getans(int u,int v){
int ret=;
int tu=top[u];
int tv=top[v];
while(tu!=tv){
if(depth[tu]<depth[tv]){
swap(tu,tv);swap(u,v);
}
ret=ret+Querysum(,idx[tu],idx[u]);
u=father[tu];
if(Querycolor(,idx[u])==Querycolor(,idx[tu]))--ret;
tu=top[u];
}
if(depth[u]>depth[v])swap(u,v);
ret=ret+Querysum(,idx[u],idx[v]);
return ret;
} int minit(){
temp=cntedge=;
memset(heavyson,,sizeof(heavyson));
memset(head,,sizeof(head));
} int main(){
scanf("%d%d",&n,&m);
minit(); for(int i=;i<=n;++i)scanf("%d",&incolor[i]);
for(int i=;i<=n-;++i){
int x,y;
scanf("%d%d",&x,&y);
addedge(x,y);addedge(y,x);
}
dfs1(,);
dfs2(,);
Build(,,n); char opty[];
while(m--){
int x,y,z;
scanf("%s",opty);
if(opty[]=='C'){
scanf("%d%d%d",&x,&y,&z);
Change(x,y,z);
}else{
scanf("%d%d",&x,&y);
printf("%d\n",Getans(x,y));
}
}
return ;
}

BZOJ:2243: [SDOI2011]染色的更多相关文章

  1. BZOJ 2243: [SDOI2011]染色 [树链剖分]

    2243: [SDOI2011]染色 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 6651  Solved: 2432[Submit][Status ...

  2. bzoj 2243 [SDOI2011]染色(树链剖分,线段树)

    2243: [SDOI2011]染色 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 4637  Solved: 1726[Submit][Status ...

  3. Bzoj 2243: [SDOI2011]染色 树链剖分,LCT,动态树

    2243: [SDOI2011]染色 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 5020  Solved: 1872[Submit][Status ...

  4. bzoj 2243: [SDOI2011]染色 线段树区间合并+树链剖分

    2243: [SDOI2011]染色 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 7925  Solved: 2975[Submit][Status ...

  5. bzoj 2243: [SDOI2011]染色 (树链剖分+线段树 区间合并)

    2243: [SDOI2011]染色 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 9854  Solved: 3725[Submit][Status ...

  6. BZOJ 2243: [SDOI2011]染色 树链剖分 倍增lca 线段树

    2243: [SDOI2011]染色 Time Limit: 20 Sec  Memory Limit: 256 MB 题目连接 http://www.lydsy.com/JudgeOnline/pr ...

  7. BZOJ 2243: [SDOI2011]染色 树链剖分+线段树区间合并

    2243: [SDOI2011]染色 Description 给定一棵有n个节点的无根树和m个操作,操作有2类: 1.将节点a到节点b路径上所有点都染成颜色c: 2.询问节点a到节点b路径上的颜色段数 ...

  8. bzoj 2243 [SDOI2011]染色(树链剖分+线段树合并)

    [bzoj2243][SDOI2011]染色 2017年10月20日 Description 给定一棵有n个节点的无根树和m个操作,操作有2类: 1.将节点a到节点b路径上所有点都染成颜色c: 2.询 ...

  9. 洛谷 P2486 [SDOI2011]染色/bzoj 2243: [SDOI2011]染色 解题报告

    [SDOI2011]染色 题目描述 给定一棵有n个节点的无根树和m个操作,操作有2类: 1.将节点a到节点b路径上所有点都染成颜色c: 2.询问节点a到节点b路径上的颜色段数量(连续相同颜色被认为是同 ...

  10. BZOJ 2243 [SDOI2011]染色 (树链剖分)(线段树区间修改)

    [SDOI2011]染色 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 6870  Solved: 2546[Submit][Status][Disc ...

随机推荐

  1. 【Go语言系列】2.2、Go语言基本程序结构:关键字与标识符

    什么是标识符 标识符用来命名变量.类型等程序实体.标识符是指Go语言对各种变量.方法.函数等命名时使用的字符序列,标识符由若干个字母.下划线_.和数字组成,且第一个字符必须是字母.通俗的讲就是凡可以自 ...

  2. WebEx如何录制电脑内的声音

    WebEx如何录制电脑内的声音     事情是这样的,我需要参加一个网络课程,视频讲课的,但是呢,又因为自己白天需要干别的事,就想着怎么把视频录下来晚上回去看,找了WebEx录屏软件,尝试了下,录屏听 ...

  3. Slim安装以及使用

    最近在用backbone.js 做东西,因为牵扯到REST services 所以需要后台支持,此处选择了php.Slim 是php的一个框架. 貌似国内文章对此的介绍比较少,在安装Slim的过程中出 ...

  4. Sweet Round 1题解

    感谢各位参赛者,所有的题解如下: T1 syx的奖励 这题明显是签到题了吧,随便猜猜结论就A掉了 先说怎么做吧,把所有的可走的数gcd起来,然后再与n求gcd 如果为1,则输出n,若不为1,则输出-1 ...

  5. 蓝牙 BLE 协议学习: 001-BLE协议栈整体架构

    背景 在深入BLE协议帧之前,我们先看一下BLE协议栈整体架构. 转载自:<深入浅出低功耗蓝牙(BLE)协议栈> 架构 如上图所述,要实现一个BLE应用,首先需要一个支持BLE射频的芯片, ...

  6. dmp文件自动分析

    dmp文件的分析,可以借助各种工具,比如WinDbg, CDB , NTSD,KD等.Windbg提供了窗口接口,而CDB , NTSD是基于命令行的工具,它们都使用了同样的调试引擎Dbgeng.dl ...

  7. spark shuffle发展历程

    spark2.3 shuffle manager,默认sortShuffleManager // Let the user specify short names for shuffle manage ...

  8. 2020/2/21 fiyocms代码审计

    0x00 前言 上午上了网课,一上午就装好了cms,下午还有网课,要是结束的早就进行审计. 解决了一下phpstudy使用过程中: Forbidden You don't have permissio ...

  9. 每天一点点之 uni-app 框架开发 - 页面滚动到指定位置

    项目需求:在页面中,不管位于何处,点击评论按钮页面滚动到对应到位置 实现思路如下: uni.createSelectorQuery().select(".comment").bou ...

  10. JDK源码阅读-------自学笔记(一)(java.lang.Object重写toString源码)

    一.前景提要 Object类中定义有public String toString()方法,其返回值是 String 类型. 二.默认返回组成 类名+@+16进制的hashcode,当使用打印方法打印的 ...