https://www.lydsy.com/JudgeOnline/problem.php?id=2288

ftiasch 18岁生日的时候,lqp18_31给她看了一个神奇的序列 A1A2, ..., AN. 她被允许选择不超过 M 个连续的部分作为自己的生日礼物。

自然地,ftiasch想要知道选择元素之和的最大值。你能帮助她吗?

这题很像BZOJ1150:[APIO/CTSC2007]数据备份,但如果没有做过的话其实也不要紧。

参考:https://www.cnblogs.com/zyfzyf/p/4114774.html感觉hzwer博客不是很好懂。

我们首先将相同符号的点缩起来,去掉首末的负结点,然后思考。

如果当前的正数个数<=m显然就求一遍和即可。

如果>m的话就有两种选择了:

1.忍痛割爱弃掉一个正数。

2.选择一个负数,将两旁正数连同负数一起缩进来。

我们发现这两个操作都是在原ans的基础上支付我们选择的点代价的,因此我们支付的代价越少越好,故我们将点权的abs放入小根堆里,每次拿出来之后和两边的点缩起来即可。

#include<map>
#include<cmath>
#include<stack>
#include<queue>
#include<cstdio>
#include<cctype>
#include<vector>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
typedef long long ll;
typedef pair<int,int>pii;
#define fi first
#define se second
const int N=1e5+;
const int INF=1e9+;
inline int read(){
int X=,w=;char ch=;
while(!isdigit(ch)){w|=ch=='-';ch=getchar();}
while(isdigit(ch))X=(X<<)+(X<<)+(ch^),ch=getchar();
return w?-X:X;
}
struct node{
int x,y;
node(int xx=,int yy=){
x=xx;y=yy;
}
bool operator <(const node &b)const{
return abs(x)>abs(b.x);
}
};
priority_queue<node>q;
int n,m,cnt,tmp,a[N],b[N],pre[N],nxt[N];
int main(){
n=read(),m=read();
for(int i=;i<=n;i++){
a[++tmp]=read();
if(!a[tmp])tmp--;
} b[++cnt]=a[];
for(int i=;i<=tmp;i++){
if((a[i]>&&a[i-]>)||(a[i]<&&a[i-]<))b[cnt]+=a[i];
else{
if(cnt==&&b[cnt]<)cnt--;
b[++cnt]=a[i];
}
}
if(b[cnt]<)cnt--; int ans=,tot=;
for(int i=;i<=cnt;i++){
if(b[i]>)ans+=b[i],tot++;
q.push(node(b[i],i));
} for(int i=;i<=cnt+;i++)pre[i]=i-,nxt[i]=i+;
pre[]=;nxt[cnt+]=cnt+;
b[]=b[cnt+]=-INF; while(tot>m){
node p=q.top();q.pop();
if(b[p.y]!=p.x)continue;
ans-=abs(p.x);
b[p.y]=b[pre[p.y]]+b[nxt[p.y]]+p.x;
b[pre[p.y]]=b[nxt[p.y]]=-INF;
q.push(node(b[p.y],p.y));
pre[p.y]=pre[pre[p.y]];nxt[pre[p.y]]=p.y;
nxt[p.y]=nxt[nxt[p.y]];pre[nxt[p.y]]=p.y;
tot--;
}
printf("%d\n",ans);
return ;
}

+++++++++++++++++++++++++++++++++++++++++++

+本文作者:luyouqi233。               +

+欢迎访问我的博客:http://www.cnblogs.com/luyouqi233/ +

+++++++++++++++++++++++++++++++++++++++++++

BZOJ2288:[POJ Challenge]生日礼物——题解的更多相关文章

  1. [bzoj2288][POJ Challenge]生日礼物

    用堆维护双向链表来贪心... 数据范围显然不容许O(nm)的傻逼dp>_<..而且dp光是状态就n*m个了..显然没法优化 大概就会想到贪心乱搞了吧...一开始想贪心地通过几段小的负数把正 ...

  2. BZOJ3502PA2012Tanie linie&BZOJ2288[POJ Challenge]生日礼物——模拟费用流+链表+堆

    题目描述 n个数字,求不相交的总和最大的最多k个连续子序列. 1<= k<= N<= 1000000. 输入 输出 样例输入 5 2 7 -3 4 -9 5 样例输出 13   根据 ...

  3. BZOJ2288:[POJ Challenge]生日礼物

    浅谈堆:https://www.cnblogs.com/AKMer/p/10284629.html 题目传送门:https://lydsy.com/JudgeOnline/problem.php?id ...

  4. bzoj2288【POJ Challenge】生日礼物*

    bzoj2288[POJ Challenge]生日礼物 题意: 给一个序列,求不超过m个连续的部分,使元素和最大.序列大小≤100000 题解: 先把连续的正数和负数合并起来,接着如果正数个数小于m则 ...

  5. BZOJ2288: 【POJ Challenge】生日礼物

    2288: [POJ Challenge]生日礼物 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 284  Solved: 82[Submit][St ...

  6. [bzoj2288]【POJ Challenge】生日礼物_贪心_堆

    [POJ Challenge]生日礼物 题目大意:给定一个长度为$n$的序列,允许选择不超过$m$个连续的部分,求元素之和的最大值. 数据范围:$1\le n, m\le 10^5$. 题解: 显然的 ...

  7. 2288.【POJ Challenge】生日礼物 链表+堆+贪心

    BZOJ2288 [POJ Challenge]生日礼物 题意: 给一个长度为\(n\)的数组,最多可以选\(m\)个连续段,问选取的最大值是多少 题解: 先把连续的符号相同的值合并,头和尾的负数去掉 ...

  8. 【链表】BZOJ 2288: 【POJ Challenge】生日礼物

    2288: [POJ Challenge]生日礼物 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 382  Solved: 111[Submit][S ...

  9. bzoj 2288 【POJ Challenge】生日礼物 双向链表+堆优化

    2288: [POJ Challenge]生日礼物 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1003  Solved: 317[Submit][ ...

随机推荐

  1. 《spark机器学习 第二版》 蔡立宇 分享 pdf下载

    链接:https://pan.baidu.com/s/15Y14eAnfj8zf5mXdixbVeQ 提取码:rkdt

  2. Siki_Unity_4-4_丛林战争_Socket/TCP网络游戏开发

    Unity 4-4 丛林战争(Socket/TCP网络游戏开发) 任务1:素材.演示.Prerequisite 使用c#的有关TCP的底层API进行服务器端的开发(直接通过socket进行通信) 功能 ...

  3. vue-scroller实现vue单页面的上拉加载和下拉刷新问题

    在vue中如何简单的实现页面的上拉加载和下拉刷新,在这里我推荐使用vue-scrolle插件. vue-scrolle的基本使用方法: 1.下载 npm i vue-scroller -D 2.导包 ...

  4. Eclipse web项目更改项目名称

    1. 右键工程:Refactor->Rename,更改项目名称: 2. 修改项目目录下:.project文件 <?xml version="1.0" encoding= ...

  5. 前端基础css

    CSS主要学习的是选择器和样式属性. 导入css的方式:行内样式,内部样式,外部样式(推荐使用) 行内样式:在标记的style属性中设定CSS样式 <p style="color: g ...

  6. Python 利用 BeautifulSoup 爬取网站获取新闻流

    0. 引言 介绍下 Python 用 Beautiful Soup 周期性爬取 xxx 网站获取新闻流: 图 1 项目介绍 1. 开发环境 Python: 3.6.3 BeautifulSoup:   ...

  7. LeetCode-63.不同路径Ⅱ

    一个机器人位于一个 m x n 网格的左上角 (起始点在下图中标记为“Start” ). 机器人每次只能向下或者向右移动一步.机器人试图达到网格的右下角(在下图中标记为“Finish”). 现在考虑网 ...

  8. linux命令系列 stat & touch

    1. stat - display file or file system status stat命令主要用于显示文件或文件系统的状态,详细信息 事实上,stat命令显示的是文件的I节点信息.Linu ...

  9. js格式化json字符串和json对象

    1,格式化json对象 var json = {"@odata.context":"$metadata#AddTableOne_466281s","v ...

  10. oracle将多个结果集用逗号拼接成字符串

    有两个函数wmsys.wm_concat和listagg 1,SELECT wmsys.wm_concat(CATALOG_NAME) FROM "DATASHARE"." ...