C++解题报告:连续的“包含”子串长度——(线段树+尺取法)

题目描述

区间查询和修改

给定N,K,M(N个整数序列,范围1~K,M次查询或修改)

如果是修改,则输入三个数,第一个数为1代表修改,第二个数为将N个数中第i个数做修改,第三个数为修改成这个数(例如1 3 5就是修改数组中第3个数,使之变为5)

如果是查询,则输入一个数2,查询N个数中包含1~K每一个数的最短连续子序列的长度

输入格式

第一行包含整数N、K和M(1 ≤ N,M ≤ 100000,1 ≤ K ≤ 50)

第二行输入N个数,用空格隔开,组成该数组

然后M行表示查询或修改

• “1 p v” - change the value of the pth number into v (1 ≤ p ≤ N,1 ≤ v ≤ K)

• “2” - what is the length of the shortest contiguous subarray of the array containing all the integers from 1 to K

输出格式

输出必须包含查询的答案,如果不存在则输出-1

样例

样例输入1

4 3 5
2 3 1 2
2
1 3 3
2
1 1 1
2

样例输出1

3
-1
4

样例输入2

6 3 6
1 2 3 2 1 1
2
1 2 1
2
1 4 1
1 6 2
2

样例输出2

3
3
4

思路详解

好题啊!!!(毒瘤,恶心。。。)

初步讨论

不用多说,看到区间马上想到线段树,而包含1到k每个数的最小子序列是个什么玩意儿???

接下来就要用尺取法了,想象两个指针curL和curR,不满足条件就将curR在区间上右移(扩大子序列),满足条件后再将curL向右移(缩小子序列),最后就可以得出答案(这个方法十分适用于连续区间和子序列之类的ÿ

posted @ 2019-07-25 15:17  Nomad_Joe_violet  阅读(7)  评论(0编辑  收藏  举报  来源