题目描述
给定一个长度为 nn且初始值全为 00的序列。你需要支持以下两种操作:
- Add L, R, hL,R,h:将序列 [L, R][L,R]内所有值小于 hh的元素都赋为 hh,此时不改变高度大于 hh的元素值
- Remove L, R, hL,R,h:将序列 [L, R][L,R]内所有值大于 hh的元素都赋为 hh,此时不改变高度小于 hh的元素值
你需要输出进行 kk次上述操作之后的序列。
解析
显然每次操作会对一段区间的取值范围造成影响,那么不妨我们维护区间取值的上下界,就可以轻松A掉这题。
最简单的方法就是线段树(不过貌似有人高级数据结构T了233)
那么维护上下界实质上也就是维护区间最大最小值,所以我们每次打个lazytag以保留操作对区间的影响就行了。注意是打标记而不是维护信息,我们不用区间查询,维护了这堆信息也没用,还浪费时间。。。
最后输出我们把lazytag造成的所有影响很好的维护出来,再遍历一次整棵线段树输出叶子节点的lazytag就行了。
那如何维护lazytag呢?我们就要关注pushdown怎么弄。
设\(up(h),down(h)\)分别对应在线段树上进行Add,Remove两种操作,改变的高度为\(h\)。
对于\(up(h)\),设改变的区间上下界为\(u,d\):
- 若\(x,不会对区间造成影响
- 若\(d,此时\(d\)变为\(x\),\(u\)不变
- 若\(x>u\),此时\(d,u\)都变为\(x\)。
参考代码
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include