题意见试题传送门

解题思路:显然是题树剖题。

考虑用线段树维护区间端点颜色与颜色数,这样就可以方便的合并,注意查询的时候对端点的特殊处理即可。

时间效率最高为\( O (m \log^{2} n) \).(BZOJ 上 4072ms)

#include <stdio.h>
#define MN 100005
#define Mn (1<<17)
#define ls(x) (x<<1)
#define rs(x) (x<<1|1)
#define mid (l+r>>1)
int lc[Mn<<],rc[Mn<<],sum[Mn<<],mark[Mn<<];
int n,q,col[MN],siz[MN],fa[MN],son[MN],dep[MN],top[MN],pos[MN],head[MN],cnt,dfsn,rev[MN];
int to[MN<<],nxt[MN<<];
inline int in(){
int x=;bool f=; char ch=getchar();
while(ch<''||ch>'') f=ch=='-',ch=getchar();
while(ch>=''&&ch<='') x=(x<<)+(x<<)+ch-'',ch=getchar();
return f?-x:x;
}
inline void swp(int &a,int &b){a^=b^=a^=b;}
inline void ins(int x,int y){to[++cnt]=y,nxt[cnt]=head[x],head[x]=cnt;}
inline void dfs1(int u,int f,int d){
fa[u]=f,dep[u]=d,siz[u]=;
for (register int i=head[u]; i; i=nxt[i])
if (to[i]!=f){
dfs1(to[i],u,d+);siz[u]+=siz[to[i]];
if (siz[to[i]]>siz[son[u]]) son[u]=to[i];
}
}
inline void dfs2(int u,int tp){
top[u]=tp;pos[u]=(++dfsn);rev[dfsn]=u;if (son[u]) dfs2(son[u],tp);
for (register int i=head[u]; i; i=nxt[i])
if (to[i]!=fa[u]&&to[i]!=son[u]) dfs2(to[i],to[i]);
}
inline void pushdown(int k){
mark[ls(k)]=mark[rs(k)]=lc[ls(k)]=rc[ls(k)]=lc[rs(k)]=rc[rs(k)]=mark[k];
sum[ls(k)]=sum[rs(k)]=;mark[k]=;
}
inline void combine(int k){
sum[k]=rc[ls(k)]==lc[rs(k)]?sum[ls(k)]+sum[rs(k)]-:sum[ls(k)]+sum[rs(k)];
lc[k]=lc[ls(k)],rc[k]=rc[rs(k)];
}
inline void build(int k,int l,int r){
mark[k]=;
if (l==r){sum[k]=,lc[k]=rc[k]=col[rev[l]];return;}
build(ls(k),l,mid);build(rs(k),mid+,r);combine(k);
}
inline void A(int l,int r,int a,int b,int k,int col){
if (a<=l&&r<=b){mark[k]=lc[k]=rc[k]=col;sum[k]=;return;}
if (mark[k]) pushdown(k);if (a<=mid) A(l,mid,a,b,ls(k),col);
if (b>mid) A(mid+,r,a,b,rs(k),col);combine(k);
}
inline int Qs(int l,int r,int a,int b,int k){
if (l==a&&r==b) return sum[k];if (mark[k]) pushdown(k);
if (b<=mid) return Qs(l,mid,a,b,ls(k));
if (a>mid) return Qs(mid+,r,a,b,rs(k));
return Qs(l,mid,a,mid,ls(k))+Qs(mid+,r,mid+,b,rs(k))-(rc[ls(k)]==lc[rs(k)]);
}
inline int Qc(int l,int r,int x,int k){
if (l==r) return lc[k];if (mark[k]) pushdown(k);
if (x<=mid) return Qc(l,mid,x,ls(k));return Qc(mid+,r,x,rs(k));
}
inline void update(int x,int y,int cl){
while (top[x]!=top[y]){
if (dep[top[x]]<dep[top[y]]) swp(x,y);
A(,n,pos[top[x]],pos[x],,cl);x=fa[top[x]];
}if (dep[x]>dep[y]) swp(x,y);A(,n,pos[x],pos[y],,cl);
}
inline int query(int x,int y){
register int res=;
while(top[x]!=top[y]){
if (dep[top[x]]<dep[top[y]]) swp(x,y);
res+=Qs(,n,pos[top[x]],pos[x],)-(Qc(,n,pos[top[x]],)==Qc(,n,pos[fa[top[x]]],));
x=fa[top[x]];
}if (dep[x]>dep[y]) swp(x,y);res+=Qs(,n,pos[x],pos[y],);return res;
}
void init(){
n=in(),q=in();for (int i=; i<=n; ++i) col[i]=in();
for (register int i=; i<n; ++i){
register int x=in(),y=in();
ins(x,y); ins(y,x);
}dfs1(,,);dfs2(,);build(,,n);
}
void solve(){
while(q--){
register char ch=getchar();while (ch!='C'&&ch!='Q') ch=getchar();
register int x=in(),y=in();
if (ch=='C') update(x,y,in());
else printf("%d\n",query(x,y));
}
}
int main(){init(); solve(); return ;}

【BZOJ2243】【SDOI2011】染色的更多相关文章

  1. BZOJ2243 SDOI2011 染色 【树链剖分】

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

  2. bzoj2243[SDOI2011]染色 树链剖分+线段树

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

  3. [bzoj2243][SDOI2011]染色

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

  4. BZOJ2243[SDOI2011]染色——树链剖分+线段树

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

  5. [BZOJ2243][SDOI2011]染色 解题报告|树链剖分

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

  6. BZOJ2243 [SDOI2011]染色(树链剖分+线段树合并)

    题目链接 BZOJ2243 树链剖分 $+$ 线段树 线段树每个节点维护$lc$, $rc$, $s$ $lc$代表该区间的最左端的颜色,$rc$代表该区间的最右端的颜色 $s$代表该区间的所有连续颜 ...

  7. BZOJ2243: [SDOI2011]染色(树链剖分/LCT)

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

  8. bzoj2243: [SDOI2011]染色--线段树+树链剖分

    此题代码量较大..但是打起来很爽 原本不用lca做一直wa不知道为什么.. 后来改lca重打了一遍= =结果一遍就AC了orz 题目比较裸,也挺容易打,主要是因为思路可以比较清晰 另:加读入优化比没加 ...

  9. BZOJ2243——[SDOI2011]染色

    1.题目大意:给个树,然后树上每个点都有颜色,然后会有路径的修改,有个询问,询问一条路径上的颜色分成了几段 2.分析:首先这个修改是树剖可以做的,对吧,但是这个分成了几段怎么搞呢,我们的树剖的不是要建 ...

  10. bzoj2243 sdoi2011 染色 paint

    明明是裸树剖 竟然调了这么久好蛋疼 大概是自己比较水的原因吧 顺便+fastio来gangbang #include<iostream> #include<cstring> # ...

随机推荐

  1. Beta版本展示

    Beta版本展示 开发团队:MyGod 团队成员:程环宇 张芷祎 王田路 张宇光 王婷婷 源码地址:https://github.com/WHUSE2017/MyGod MyGod团队项目的目标: 让 ...

  2. Tornado 网站demo 二

    连接数据库 methods 中建立一个文件 db.py 分别建立起连接对象和游标对象 #!/usr/bin/env Python # coding=utf-8 import pymysql conn ...

  3. 山西某公司NetApp存储不小心删除文件数据恢复成功案例

    故障情况简介: 需要进行数据恢复的设备是一台NetApp存储,共有24块磁盘组成.由于管理员删除文件夹,且时间比较久,删除有几个月时间. 可恢复性判断:由于NetApp中的文件系统的特性,WAFL是& ...

  4. ebtables和iptables与linux bridge的交互

    本文为翻译文,不一定是逐字逐句的翻译,而且中间会加上自己的一点见解,如有理解错误的地方,还请大家指出,我定虚心学习.原文见链接 其中斜体字是自己的理解,建议和ebtables手册和iptables手册 ...

  5. Docker_部署jenkins(dockerfile实现)

    docker+jenkins开始合体! 我用的是ubuntu14.04的基础镜像,具体的这里不做赘述. 我在/tmp/目录下建了一个Dockerfile文件: touch Dockerfile vi ...

  6. 记一次向maven中央仓库提交依赖包

    Maven是Java中最常用的依赖管理工具,Maven的中央仓库保罗万象,涵盖了各个领域的框架.工具和文档,也是Java生态强大生命力的体现.我们自己开发的一些有用有趣的代码也可以通过打包上传到mav ...

  7. node express将请求重定向为https

    项目开发时,由于服务器只接受https请求(运维说了算...),所以在生产环境时,要把所有http请求全都重定向为https,具体操作是在app.js文件里加入以下代码: var express = ...

  8. Python/MySQL(一、基础)

    Python/MySQL(一.基础) mysql: MYSQL : 是用于管理文件的一个软件 -socket服务端 (先启动) -本地文件操作 -解析 指令[SQL语句] -客户端软件 (各种各样的客 ...

  9. 一种dubbo逻辑路由方案(服务化隔离环境)

    背景介绍 现在很多的公司都在用dubbo.springcloud做为服务化/微服务的开发框架,服务化之后应用越来越多,链路越来越长,服务环境的治理变的很困难.比如:研发团队的人很多的,同时有几个分支在 ...

  10. spark2.1:在RDD[unit].foreach(s=>{})内部调用sparkSession对象抛出NullPointException

    问题代码: val sample_data_combine_result=List( (0,(List(FitModel(4022,1447.92,-8.38983306721434,2.0),Fit ...