博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
[luogu2486] [SDOI2011]染色
阅读量:5282 次
发布时间:2019-06-14

本文共 2552 字,大约阅读时间需要 8 分钟。

emmmm裸的树剖,但是考点好像是在线段树上……

如何维护一个区间里有多少个连续相同的数字块呢?考虑对于\(a\)\(b\)两个区间,如果他们相接的端点颜色相同,那么合并出的新区间的\(seg = seg[a] + seg[b] - 1\),否则就是\(seg = seg[a] + seg[b]\)

这就是pushup操作了,但是懒标记怎么下推?直接把区间\(seg = 1\)即可,因为这一个区间颜色都一样了,但是两个端点的颜色要注意修改。

那问题到了剖分:一条路径由多条树链组成,树链首尾相连,也要考虑相接端点。

#include 
#include
#include
#define MAXN 100005#define lson (rt<<1)#define rson (rt<<1|1)#define mid ((l+r)>>1)struct edge { int v,next;}G[MAXN<<1];int head[MAXN];struct Node { int u,from;};int val[MAXN],a[MAXN];int seg[MAXN<<2],tag[MAXN<<2];int dfn[MAXN],top[MAXN];int size[MAXN],son[MAXN],fa[MAXN],d[MAXN];int N,M,tot = 0,num = 0;inline void add(int u,int v) { G[++tot].v = v;G[tot].next = head[u];head[u] = tot;}inline void pushup(int rt,int l,int r) { seg[rt] = seg[lson] + seg[rson]; if(val[mid]==val[mid+1]) seg[rt]--;}void Build(int rt,int l,int r) { tag[rt] = 0; if(l==r) { seg[rt] = 1; return; } Build(lson,l,mid); Build(rson,mid+1,r); pushup(rt,l,r);}inline void pushdown(int rt,int l1,int r1,int l2,int r2) { if(tag[rt]==0) return; tag[lson] = tag[rson] = tag[rt]; seg[lson] = seg[rson] = 1; val[l1] = val[r1] = val[l2] = val[r2] = tag[rt]; tag[rt] = 0;}void update(int C,int L,int R,int rt,int l,int r) { if(L<=l&&R>=r) { seg[rt] = 1; tag[rt] = C; val[l] = val[r] = C; return; } if(L>r||R
mid) update(C,L,R,rson,mid+1,r); pushup(rt,l,r);}int query(int L,int R,int rt,int l,int r) { if(L<=l&&R>=r) return seg[rt]; if(L>r||R
mid) right = query(L,R,rson,mid+1,r); pushup(rt,l,r); int r1 = mid,l2 = mid+1; if(left==0) return right; else if(right==0) return left; else if(val[r1]==val[l2]) return left+right-1; else return left+right; }void dfs1(int u,int father) { d[u] = d[father] + 1;size[u] = 1; fa[u] = father;son[u] = 0; for(int i=head[u];i;i=G[i].next) { int v = G[i].v;if(v==father) continue; dfs1(v,u); size[u] += size[v]; if(size[son[u]]
d[v.u]) std::swap(u,v); ans += query(dfn[u.u],dfn[v.u],1,1,N); if(u.from!=0&&val[u.from]==val[dfn[u.u]]) ans--; if(v.from!=0&&val[v.from]==val[dfn[v.u]]) ans--; return ans; }inline void chain_update(int x,int y,int w) { while(top[x]!=top[y]) { if(d[top[x]]
d[y]) std::swap(x,y); update(w,dfn[x],dfn[y],1,1,N);}int main() { int u,v; scanf("%d%d",&N,&M); for(int i=1;i<=N;++i) { scanf("%d",&a[i]); } for(int i=1;i

转载于:https://www.cnblogs.com/Neworld2002/p/10009363.html

你可能感兴趣的文章
MVC学习系列——Model验证扩展
查看>>
字符串
查看>>
vue2.x directive - 限制input只能输入正整数
查看>>
实现MyLinkedList类深入理解LinkedList
查看>>
自定义返回模型
查看>>
C#.NET 大型通用信息化系统集成快速开发平台 4.1 版本 - 客户端多网络支持
查看>>
HDU 4122
查看>>
Suite3.4.7和Keil u3自带fx2.h、fx2regs.h文件的异同
查看>>
打飞机游戏【来源于Crossin的编程教室 http://chuansong.me/account/crossincode 】
查看>>
[LeetCode] Merge Intervals
查看>>
【翻译自mos文章】当点击完 finishbutton后,dbca 或者dbua hang住
查看>>
Linux编程简介——gcc
查看>>
2019年春季学期第四周作业
查看>>
MVC4.0 利用IActionFilter实现简单的后台操作日志功能
查看>>
rotate the clock
查看>>
bugku 变量
查看>>
数据库01 /Mysql初识以及基本命令操作
查看>>
数据库02 /MySQL基础数据类型以及多表之间建立联系
查看>>
Python并发编程04/多线程
查看>>
CF461B Appleman and Tree
查看>>