【BZOJ3638】Cf172 k-Maximum Subsequence Sum

Description

给一列数,要求支持操作: 1.修改某个数的值 2.读入l,r,k,询问在[l,r]内选不相交的不超过k个子段,最大的和是多少。1 ≤ n ≤ 105,1 ≤ m ≤ 105,1 ≤ l ≤ r ≤ n, 1 ≤ k ≤ 20

Sample Input

9
9 -8 9 -1 -1 -1 9 -8 9
3
1 1 9 1
1 1 9 2
1 4 6 3

Sample Output

17
25
0

题解:如果直接用背包DP跑线段树区间合并的话,复杂度是O(nk^2logn)的

先考虑费用流的做法,我们第一次取的时候一定选择的是区间中的最大连续子段,然后模拟费用流的过程,我们建立反向边,即将原来的最大连续子段取反,然后再找最大连续子段。。。最后询问完毕,再将哪些取反操作都还原回去。

所以一共要维护哪些东西呢?最大连续子段和以及它的位置,不过由于有取反操作,所以我们还要维护最小连续子段和以及它的位置,然后就没了。。。

为了代码美观,区间合并的时候用了很多重载运算符,还是挺吓人的~

#include <cstdio>
#include <cstring>
#include <iostream>
#define lson x<<1
#define rson x<<1|1
const int maxn=100010;
using namespace std;
int n,m,ans;
int v[maxn],pa[maxn],pb[maxn];
struct pp
{
int val,l,r;
pp() {}
pp(int x) {l=r=x,val=v[x];}
pp(int a,int b,int c) {val=a,l=b,r=c;}
pp operator + (const pp &a) const {return pp(val+a.val,l,a.r);}
bool operator < (const pp a) const {return val<a.val;}
};
struct node
{
bool tag;
pp s,sm,sn,lm,ln,rm,rn;
node() {}
node(int x)
{
s=pp(x),tag=0;
if(v[x]<0) ln=rn=sn=s,lm=sm=pp(0,x,x-1),rm=pp(0,x+1,x);
else lm=rm=sm=s,ln=sn=pp(0,x,x-1),rn=pp(0,x+1,x);
}
}s[maxn<<2];
inline int rd()
{
int ret=0,f=1; char gc=getchar();
while(gc<'0'||gc>'9') {if(gc=='-')f=-f; gc=getchar();}
while(gc>='0'&&gc<='9') ret=ret*10+gc-'0',gc=getchar();
return ret*f;
}
inline int max(int a,int b,int c) {return max(max(a,b),c);}
inline int min(int a,int b,int c) {return min(min(a,b),c);}
inline pp max(const pp &a,const pp &b,const pp &c) {return max(max(a,b),c);}
inline pp min(const pp &a,const pp &b,const pp &c) {return min(min(a,b),c);}
inline node merge(const node &a,const node &b)
{
node c;
c.lm=max(a.lm,a.s+b.lm),c.rm=max(b.rm,a.rm+b.s),c.sm=max(a.sm,b.sm,a.rm+b.lm);
c.ln=min(a.ln,a.s+b.ln),c.rn=min(b.rn,a.rn+b.s),c.sn=min(a.sn,b.sn,a.rn+b.ln);
c.s=a.s+b.s,c.tag=0;
return c;
}
inline void rev(node &x)
{
x.sm.val=-x.sm.val,x.lm.val=-x.lm.val,x.rm.val=-x.rm.val;
x.sn.val=-x.sn.val,x.ln.val=-x.ln.val,x.rn.val=-x.rn.val;
x.s.val=-x.s.val,x.tag^=1;
swap(x.sm,x.sn),swap(x.lm,x.ln),swap(x.rm,x.rn);
}
inline void pushdown(int x)
{
if(s[x].tag) rev(s[lson]),rev(s[rson]),s[x].tag=0;
}
void build(int l,int r,int x)
{
if(l==r)
{
s[x]=node(l);
return ;
}
int mid=(l+r)>>1;
build(l,mid,lson),build(mid+1,r,rson);
s[x]=merge(s[lson],s[rson]);
}
void updata(int l,int r,int x,int a,int b)
{
if(a<=l&&r<=b)
{
rev(s[x]);
return ;
}
pushdown(x);
int mid=(l+r)>>1;
if(a<=mid) updata(l,mid,lson,a,b);
if(b>mid) updata(mid+1,r,rson,a,b);
s[x]=merge(s[lson],s[rson]);
}
node query(int l,int r,int x,int a,int b)
{
if(a<=l&&r<=b) return s[x];
pushdown(x);
int mid=(l+r)>>1;
if(b<=mid) return query(l,mid,lson,a,b);
if(a>mid) return query(mid+1,r,rson,a,b);
return merge(query(l,mid,lson,a,b),query(mid+1,r,rson,a,b));
}
void modify(int l,int r,int x,int a)
{
if(l==r)
{
s[x]=node(l);
return ;
}
pushdown(x);
int mid=(l+r)>>1;
if(a<=mid) modify(l,mid,lson,a);
else modify(mid+1,r,rson,a);
s[x]=merge(s[lson],s[rson]);
}
int main()
{
n=rd();
int i,j,a,b,c;
pp tmp;
for(i=1;i<=n;i++) v[i]=rd();
build(1,n,1);
m=rd();
for(i=1;i<=m;i++)
{
if(rd()==1)
{
a=rd(),b=rd(),c=rd(),ans=0;
for(j=1;j<=c;j++)
{
tmp=query(1,n,1,a,b).sm,ans+=tmp.val;
if(!tmp.val) break;
pa[j]=tmp.l,pb[j]=tmp.r,updata(1,n,1,tmp.l,tmp.r);
}
for(j--;j;j--) updata(1,n,1,pa[j],pb[j]);
printf("%d\n",ans);
}
else a=rd(),b=rd(),v[a]=b,modify(1,n,1,a);
}
return 0;
}//9 9 -8 9 -1 -1 -1 9 -8 9 3 1 1 9 1 1 1 9 2 1 4 6 3

【BZOJ3638】Cf172 k-Maximum Subsequence Sum 线段树区间合并(模拟费用流)的更多相关文章

  1. 【bzoj3638】Cf172 k-Maximum Subsequence Sum 模拟费用流+线段树区间合并

    题目描述 给一列数,要求支持操作: 1.修改某个数的值 2.读入l,r,k,询问在[l,r]内选不相交的不超过k个子段,最大的和是多少. 输入 The first line contains inte ...

  2. hdu-3308 LCIS (线段树区间合并)

    LCIS Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submis ...

  3. hdu 3308(线段树区间合并)

    LCIS Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submis ...

  4. LCIS HDU - 3308 (线段树区间合并)

    LCIS HDU - 3308 Given n integers. You have two operations: U A B: replace the Ath number by B. (inde ...

  5. HDU 3911 Black And White(线段树区间合并+lazy操作)

    开始以为是水题,结果...... 给你一些只有两种颜色的石头,0为白色,1为黑色. 然后两个操作: 1 l r 将[ l , r ]内的颜色取反 0 l r 计算[ l , r ]内最长连续黑色石头的 ...

  6. poj3667 线段树 区间合并

    //Accepted 3728 KB 1079 ms //线段树 区间合并 #include <cstdio> #include <cstring> #include < ...

  7. hdu3911 线段树 区间合并

    //Accepted 3911 750MS 9872K //线段树 区间合并 #include <cstdio> #include <cstring> #include < ...

  8. 线段树(区间合并) POJ 3667 Hotel

    题目传送门 /* 题意:输入 1 a:询问是不是有连续长度为a的空房间,有的话住进最左边 输入 2 a b:将[a,a+b-1]的房间清空 线段树(区间合并):lsum[]统计从左端点起最长连续空房间 ...

  9. HDU 3308 LCIS (线段树区间合并)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3308 题目很好懂,就是单点更新,然后求区间的最长上升子序列. 线段树区间合并问题,注意合并的条件是a[ ...

随机推荐

  1. 倍福TwinCAT(贝福Beckhoff)常见问题(FAQ)-人机界面如何修改界面皮肤

    切换到视图管理器,然后可以切换皮肤,会有预览效果     更多教学视频和资料下载,欢迎关注以下信息: 我的优酷空间: http://i.youku.com/acetaohai123   我的在线论坛: ...

  2. ASP.NET中session和ViewState区别

    session变量是保存在Sever的内存中的,用的太多肯定会拖累Sever的,而且20分钟后session变量就会过期,不适合保存长期变量. ViewState是将数据保存在页面隐藏的控件中,永远不 ...

  3. [原创]如何让freeswitch转发客户端自定义的INFO消息

    如何让freeswitch转发客户端自定义的INFO消息 英文概述: this article is about how to configure freeswitch to forward self ...

  4. TensorFlow学习笔记3——Placeholders and feed_dict

    1. Placeholders placeholders,顾名思义,就是占位的意思,举个例子:我们定义了一个关于x,y的函数 f(x,y)=2x+y,但是我们并不知道x,y的值,那么x,y就是等待确定 ...

  5. gitlab 6 安装备忘录

    gitlab 6.2-stable;Ubuntu 13.10;ruby 2.0.0 推荐使用PostgreSQL,MySQL不同版本可能碰到兼容性问题(www.oschina.net/question ...

  6. rxjs来啦

    var text = document.querySelector('#text'); var inputStream = Rx.Observable.fromEvent(text, 'keyup') ...

  7. 一次httpserver优化的经验和教训(silverlight游戏 - 金庸群侠传X0.5上线记)

    金X因为被推荐到ACFUN游戏排行第一名.并同一时候在17YY.7K7K.U77.17173等各大小游戏站点上线.迎来了在线用户数量的爆炸式增长.眼下各大站点使用外链方式.也就是实际链接到金X官网的s ...

  8. LeetCode 75 Sort Colors(颜色排序)

    翻译 给定一个包括红色.白色.蓝色这三个颜色对象的数组.对它们进行排序以使同样的颜色变成相邻的,其顺序是红色.白色.蓝色. 在这里,我们将使用数字0.1和2分别来代表红色.白色和蓝色. 原文 Give ...

  9. UML类图详解_关联关系_多对多

    在关联关系中,很多情况下我们的多重性并不是多对一或者一对多的,而是多对多的. 不过因为我们要考虑里面的导航性,如果直接搞的话就是需要去维护两群对象之间多对多的互指链接,这就十分繁杂且易错.那么我们怎么 ...

  10. SpringBoot支持https和http

    1.application.propertites #server.port=8081 server.port: 8443 server.ssl.key-store: classpath:keysto ...