南昌网络赛 I. Max answer (单调栈 + 线段树)
https://nanti.jisuanke.com/t/38228
题意
给你一个序列,对于每个连续子区间,有一个价值,等与这个区间和×区间最小值,
求所有子区间的最大价值是多少。
分析:我们先用单调栈预处理 区间 [L[i] , R[i] ] 最小值为a[i] , 的L[i] , R[i] ;
首先我们明白 , 如果a[i] >0 那 [L[i] , R[i] ] , 里面的数都是正数 , 所以应该全选 ;
a[i] < 0 , 那我们 应该在[L[i]-1 , i-1] 这里面找到前缀和最大 , 在[i,R[i]] 这里找到前缀和最小
这样的区间和才是最大
我。。。比赛的时候被自己秀死 , 判断a[i] >0 竟然也用了线段树的做法 , 导致边界没有控制好
#include <iostream>
#include <string.h>
#include <algorithm>
#include <stdio.h>
#include <math.h>
#include <queue>
#define MAXN 500001
#define inf 0x3f3f3f3f using namespace std;
const int N=;
typedef long long ll; int a[N],L[N],R[N],s[N],top;
ll sum[N],ans=-0x7f7f7f7f,n,h[N];
ll l=,r=;
struct node{
int l,r;//区间[l,r] ll mx; //区间最大值
ll mn; //区间最小值
}tree[MAXN<<];//一定要开到4倍多的空间 void pushup(int index){ tree[index].mx = max(tree[index<<].mx,tree[index<<|].mx);
tree[index].mn = min(tree[index<<].mn,tree[index<<|].mn);
} int cnt;
void build(int l,int r,int index){
tree[index].l = l;
tree[index].r = r; if(l == r){
// scanf("%d",&tree[index].sum);
tree[index].mn = tree[index].mx =sum[++cnt];
return ;
}
int mid = (l+r)>>;
build(l,mid,index<<);
build(mid+,r,index<<|);
pushup(index);
} ll queryMIN(int l,int r,int index){
if(l <= tree[index].l && r >= tree[index].r){
//return tree[index].sum; return tree[index].mn;
} int mid = (tree[index].l+tree[index].r)>>; ll Min =0x7f7f7f7f;
if(l <= mid){ // Max = max(query(l,r,index<<1),Max);
Min = min(queryMIN(l,r,index<<),Min);
}
if(r > mid){ // Max = max(query(l,r,index<<1|1),Max);
Min = min(queryMIN(l,r,index<<|),Min);
}
//return ans; return Min;
//return Min;
}
ll queryMAX(int l,int r,int index){
if(l <= tree[index].l && r >= tree[index].r){
//return tree[index].sum;
return tree[index].mx;
//return tree[index].mn;
} int mid = (tree[index].l+tree[index].r)>>; ll Max = -0x7f7f7f7f; if(l <= mid){ Max = max(queryMAX(l,r,index<<),Max);
// Min = min(query(l,r,index<<1),Min);
}
if(r > mid){ Max = max(queryMAX(l,r,index<<|),Max);
//Min = min(query(l,r,index<<1|1),Min);
}
//return ans; return Max;
//return Min;
}
int main()
{ ios::sync_with_stdio(false);
cin>>n;
memset(sum,,sizeof(sum));
for(int i=;i<=n;i++)
{
cin>>a[i];
sum[i]=sum[i-]+a[i]; }
build(,n+,); top=;
for(int i=;i<=n;i++)
{
while(top&&a[s[top]]>=a[i])
--top;
L[i]=(top==?:s[top]+);
s[++top]=i;
}
top=;
for(int i=n;i>=;i--)
{
while(top&&a[s[top]]>=a[i])
--top;
R[i]=(top==?n:s[top]-);
s[++top]=i;
}
// cout<<queryMIN(2,2,1)<<endl;
for(int i=;i<=n;i++)
{
ll temp;
if(a[i]>)
{ temp =(sum[R[i]] - sum[L[i]-])*a[i];
// cout<<L[i]<<" "<<R[i]<<endl;
// cout<<queryMAX(i,R[i],1)<<" "<<queryMIN(L[i]-1,i-1,1)<<endl;
}
else if(a[i]<)
{ if(L[i]== && queryMAX(max(,L[i]-),max(,i-),)<)
temp=(queryMIN(i,R[i],))*a[i];
else
temp =(queryMIN(i,R[i],)-queryMAX(max(,L[i]-),max(,i-),))*a[i]; // cout<<queryMAX(L[i]-1,i-1,1)<<" "<<queryMIN(i,R[i],1)<<endl; }
else if(a[i]==)
temp=;
// else if(a[i]<0)
// {
// temp=(queryMIN(R[i],i,1) - queryMAX(L[i],i,1))*a[i];
// }
if(temp>ans) {ans=temp;}
} cout<<ans<<endl;
}
南昌网络赛 I. Max answer (单调栈 + 线段树)的更多相关文章
- 2019ICPC南昌邀请赛网络赛 I. Max answer (单调栈+线段树/笛卡尔树)
题目链接 题意:求一个序列的最大的(区间最小值*区间和) 线段树做法:用单调栈求出每个数两边比它大的左右边界,然后用线段树求出每段区间的和sum.最小前缀lsum.最小后缀rsum,枚举每个数a[i] ...
- 网络赛 I题 Max answer 单调栈+线段树
题目链接:https://nanti.jisuanke.com/t/38228 题意:在给出的序列里面找一个区间,使区间最小值乘以区间和得到的值最大,输出这个最大值. 思路:我们枚举每一个数字,假设是 ...
- 南昌邀请赛I.Max answer 单调栈+线段树
题目链接:https://nanti.jisuanke.com/t/38228 Alice has a magic array. She suggests that the value of a in ...
- The Preliminary Contest for ICPC China Nanchang National Invitational I. Max answer (单调栈+线段树)
题目链接:https://nanti.jisuanke.com/t/38228 题目大意:一个区间的值等于该区间的和乘以区间的最小值.给出一个含有n个数的序列(序列的值有正有负),找到该序列的区间最大 ...
- 南昌网络赛 I. Max answer 单调栈
Max answer 题目链接 https://nanti.jisuanke.com/t/38228 Describe Alice has a magic array. She suggests th ...
- 洛谷P4198 楼房重建 单调栈+线段树
正解:单调栈+线段树 解题报告: 传送门! 首先考虑不修改的话就是个单调栈板子题昂,这个就是 然后这题的话,,,我怎么记得之前考试好像有次考到了类似的题目昂,,,?反正我总觉着这方法似曾相识的样子,, ...
- 2018宁夏邀请赛 L Continuous Intervals(单调栈+线段树)
2018宁夏邀请赛 L Continuous Intervals(单调栈+线段树) 传送门:https://nanti.jisuanke.com/t/41296 题意: 给一个数列A 问在数列A中有多 ...
- 2019南昌网络赛I:Yukino With Subinterval(CDQ) (树状数组套主席树)
题意:询问区间有多少个连续的段,而且这段的颜色在[L,R]才算贡献,每段贡献是1. 有单点修改和区间查询. 思路:46min交了第一发树套树,T了. 稍加优化多交几次就过了. 不难想到,除了L这个点, ...
- 2019南昌网络赛-I(单调栈+线段树)
题目链接:https://nanti.jisuanke.com/t/38228 题意:定义一段区间的值为该区间的和×该区间的最小值,求给定数组的最大的区间值. 思路:比赛时还不会线段树,和队友在这题上 ...
随机推荐
- android Service 的简单使用(转)
1.要使用Service,首先就是在配置文件里吗添加Service,如果不填加,你的Service是不能够使用的.目前学到的方法有两种 方法一:<service android:enabl ...
- linux安装mysql后root无法登录
[root@localhost mysql]# mysql -u root -pEnter password: ERROR 1045 (28000): Access denied for user ' ...
- Nginx学习基础(一)
Nginx是个可靠高效的中间件,就是跟其他语言连接,可以做为一个工具的服务器. 可以处理的问题: 1.反向代理 (1)正向代理(以客户端为主):访问网站的时候,早起是在做通过n多个路由访问网站的操作, ...
- Java学习总结——常见问题及解决方法
CYTX项目开发中遇到的问题及解决方法 Android开发各类常见错误解决方案: 使用Android Studio遇到的问题及解决过程 登录注册部分问题及解决: 1.问题:"No targe ...
- [label][JavaScript]闭包阅读笔记
原文链接来源: http://www.ruanyifeng.com/blog/2009/08/learning_javascript_closures.ht ...
- 咏南BS开发框架
咏南BS开发框架 开发工具为:DELPHI 2006及以上版本.欢迎索取演示. 通用的三级权限管理. 登录验证 输入帐号和密码验证登录系统. 功能菜单 在这里设置好菜单,系统运行的时候会根据菜单设置动 ...
- 我的"gethup"(GitHub)注册之旅
大家好,我叫张琪琪,来自网络工程143(学号1413042062),.平时喜欢运动,也喜欢看电视尤其是动漫.其实对于自己的编程能力没有多大自信,如果看着题目回忆课本内容写下的程序也算的话,那是敲过不少 ...
- [Elixir002]节点启动后自动连接其它节点
问题: 如何指定一个节点在启动后自动连接到别的节点上? 这个我们要使用到sys.config,这是erlang的配置文件,这个文件一般都是$ROOT/releases/Vsn下 1. 首先我们要先启动 ...
- QPS的计算
QPS = req/sec = 请求数/秒 Q:如何根据日志查看一个服务的qps A: 一般access.log是记录请求的日志,tail -f XXX.access.log ,可发现格式如下: 前 ...
- xml写入
XmlDocument xmlDocument=new XmlDocument(); XmlElement root = xmlDocument.CreateElement("", ...