题目链接:https://ac.nowcoder.com/acm/contest/883/F
题目描述
给你一个1到n的序列,你要找出最长的一个子序列(连续的),满足序列中所有的元素出现的次数要么为0次,要么大于等于k次。
思路
(这谁看得出来是线段树。。。。摇了我8
对于每一个位置i,维护两个东西:
last[i]表示i位置这个值上一次出现的位置
lastk[i]表示i位置这个值上k次出现的位置
那么枚举右端点i,对于每个右端点i,维护这个节点到之前所有的节点形成的区段中有多少个数组出现的次数不到k,也就是说维护区间[1,i]有多少个数字出现的次数不到k
线段树维护的就是这个区间[l,r]里面有多少个数字出现的次数不到k,那么假设我们当前右端点为i,区间【last[i]+1,i】肯定是不满足要求的,update的时候不满足要求的数就要多加1;而区间[ lastk[last[i]]+1,lastk[i] ]这个区间内,i位置的值出现了k次,所以update的时候不满足要求的数要减少1.
查询的时候就查询距离当前右端点i最远的那个不满足要求的数为0的区间的左端点,取最大就好了。