【GSS1】:
题意:给定长度为N的数串,M个询问插叙[a,b]的的最大连续子段和;
解析:线段树维护左端最大、右端最大、全局最大和整体和;然后动态插叙即可。
【GSS3】:
题意:在GSS1的基础上支持修改第i个数x的修改操作。
解析:同上
【GSS5】:
题意:在GSS1的基础上询问x1,y1,x2,y2,使得a属于[x1,y1],b属于[x2,y2];问最大的[a,b]的字段和。
解析:维护GSS1的基础上,分情况讨论
1、如果x1<=y1<x2<=y2 即区间分离,则中间必须取,分别在两端区间靠近中间选取最大可以不选
2、如果x1<=x2<=y1<=y2
①只选取[x2,y1]
②选取[x1,x2-1]最右端的部分(或不选),和[x2,y1]的最左端部分
③选取[x2,y1]的最右端部分,和[y1+1,y2]的最左端部分(或不选)
④选取[x1,x1-1]的最右端部分(或不选),[x2,y1]的全部,和[y1+1,y2]的最左端部分(或不选)
4者取最大即可。
【GSS2】:
题意:在GSS1的基础上,相等的两个元素不重复累加。
解析:看过Oimaster的解题报告后,懂得可以离线做。
传送门:http://blog.163.com/oimaster@126/blog/static/84121884201042303223894/
注意到这个题没有修改操作,因此可以采用离线算法。将询问区间排序后,我们一次加入每一个数。设s[i]表示i到当前处理的数的和。如果新加入的数为x,位置为k,则s[last[x]+1]到s[k]都要加上x。询问就像当于询问s[a]..s[b]中的最大值,注意是曾经出现过的最大值(就是说以前的也算)。我们用线段树维护s[]。要注意我们需要保存曾经最大的tag。
我是先考虑到了写两个标记……后来发现必须维护曾经最大的值和曾经最大的标记……离线算法很经典
【GSS6】
题意:在GSS1的基础上允许加入一个值,删除一个值,替换一个值。
解析:Splay维护按照线段树的方法类似维护即可。
【GSS7】
题意:求树上的GSS,允许修改某段路径的值。
解析:用Link-Cut-Tree维护一坨Splay打个标记即可。