SPOJ - GSS1 —— 线段树 (结点信息合并)
题目链接:https://vjudge.net/problem/SPOJ-GSS1
GSS1 - Can you answer these queries I
You are given a sequence A[1], A[2], ..., A[N] . ( |A[i]| ≤ 15007 , 1 ≤ N ≤ 50000 ). A query is defined as follows:
Query(x,y) = Max { a[i]+a[i+1]+...+a[j] ; x ≤ i ≤ j ≤ y }.
Given M queries, your program must output the results of these queries.
Input
- The first line of the input file contains the integer N.
- In the second line, N numbers follow.
- The third line contains the integer M.
- M lines follow, where line i contains 2 numbers xi and yi.
Output
Your program should output the results of the M queries, one query per line.
Example
Input:
3
-1 2 3
1
1 2 Output:
2
题意:
给出一个序列。有m个询问:区间[L,R]里的最大连续和是多少?
题解:
1.线段树的结点信息合并。将这n个数按线段树的形式分割下去,然后再从最底层的小区间,往上合并得到大区间:两个对应的小区间有四种合并结果(得到一段连续的区间):1.左连续、右连续、左右不连续、全连续。记录每种合并结果的最大值。
2.对于询问区间,依旧如普通的查询操作一样,拿到线段树里与对应区间,但是需要注意的是:当询问区间被mid分成两段时,需要单独单出来,然后再尝试将两段进行信息合并。
代码如下:
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <vector>
#include <queue>
#include <stack>
#include <map>
#include <string>
#include <set>
using namespace std;
typedef long long LL;
const double EPS = 1e-;
const int INF = 2e9;
const LL LNF = 2e18;
const int MAXN = 5e4+; struct node
{
int a[];
};
node sum[MAXN<<]; /*
0:两边不连续
1:左连续
2:右连续
3:全连续
*/
void push_up(int fa[], int s1[], int s2[])
{
fa[] = max(max(s1[], s2[]),max(max(s1[],s2[]), s1[]+s2[]));
fa[] = max(max(s1[],s1[]), s1[]+s2[]);
fa[] = max(max(s2[],s2[]), s1[]+s2[]);
fa[] = s1[] + s2[];
} void build(int u, int l, int r)
{
if(l==r)
{
scanf("%d", &sum[u].a[]); //只有一个点,当然是全连续
sum[u].a[] = sum[u].a[] = sum[u].a[] = -; //其他情况设为不可能
return;
} int mid = (l+r)>>;
build(u*, l, mid);
build(u*+, mid+, r);
push_up(sum[u].a, sum[u*].a, sum[u*+].a);
} node query(int u, int l, int r, int x, int y)
{
if(x<=l && r<=y)
return sum[u]; int mid = (l+r)>>;
node ret;
if(y<=mid) //询问区间在左边
ret = query(u*, l, mid, x, y);
else if(x>=mid+) //询问区间在右边
ret = query(u*+, mid+, r, x, y);
else //询问区间被分割成两段,因而还要调用push_up尝试将两子区间合并
{
node t1 = query(u*, l, mid, x, mid);
node t2 = query(u*+, mid+, r, mid+, y);
push_up(ret.a, t1.a, t2.a);
}
return ret;
} int main()
{
int n, m;
scanf("%d", &n);
build(,,n);
scanf("%d", &m);
while(m--)
{
int l, r;
scanf("%d%d", &l,&r);
node ret = query(,,n,l,r);
int t1 = max(ret.a[], ret.a[]); //取四种连续情况的最大值
int t2 = max(ret.a[], ret.a[]);
printf("%d\n", max(t1,t2));
}
}
SPOJ - GSS1 —— 线段树 (结点信息合并)的更多相关文章
- [BZOJ4552][TJOI2016&&HEOI2016]排序(二分答案+线段树/线段树分裂与合并)
解法一:二分答案+线段树 首先我们知道,对于一个01序列排序,用线段树维护的话可以做到单次排序复杂度仅为log级别. 这道题只有一个询问,所以离线没有意义,而一个询问让我们很自然的想到二分答案.先二分 ...
- HDU3308 线段树(区间合并)
LCIS Time Limit: 6000/2000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Submis ...
- 线段树:CDOJ1592-An easy problem B (线段树的区间合并)
An easy problem B Time Limit: 2000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Pr ...
- 线段树的区间合并 B - LCIS
B - LCIS HDU - 3308 这个是一个很简单很明显的线段树的区间合并,不过区间合并的题目都还是有点难写,建议存个板子. #include <cstdio> #include & ...
- SPOJ GSS3 线段树系列1
SPOJ GSS系列真是有毒啊! 立志刷完,把线段树搞完! 来自lydrainbowcat线段树上的一道例题.(所以解法参考了lyd老师) 题意翻译 n 个数, q 次操作 操作0 x y把 Ax 修 ...
- BZOJ 1018: [SHOI2008]堵塞的交通traffic [线段树 区间信息]
1018: [SHOI2008]堵塞的交通traffic Time Limit: 3 Sec Memory Limit: 162 MBSubmit: 3064 Solved: 1027[Submi ...
- 线段树(区间合并)HDU - 1540
题意:输入n,m,给定n个相互连通的村庄,有m个操作,D x,表示破坏x村庄使其与相邻的两个村庄不相通,R 表示修复上一个被破坏的村庄,与相邻的两个村庄联通.Q x表示与x相连的村庄有多少个. 思路: ...
- [HDOJ3308]LCIS(线段树,区间合并)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3308 题意:给定n个数,两个操作: U A B:将位置A的数值改成B Q A B:查询[A,B]内最长 ...
- POJ 2750 Potted Flower(线段树的区间合并)
点我看题目链接 题意 : 很多花盆组成的圆圈,每个花盆都有一个值,给你两个数a,b代表a位置原来的数换成b,然后让你从圈里找出连续的各花盆之和,要求最大的. 思路 :这个题比较那啥,差不多可以用DP的 ...
随机推荐
- 安装XAMPP时出现 unable to realloc 83886080 bytes
参考:https://www.apachefriends.org/faq_linux.html 转载:http://blog.xinspace.space/2015/08/06/xampp-unabl ...
- opencv-2.4.11编译备忘
编译完成后,想测试example中例子,但是由于没有sudo权限,不能运行pkg-config查看opencv的--cflags和--libs. 记录一下,备忘: pkg-config --libs ...
- Java设计模式博客全文件夹
转载请注明出处:http://blog.csdn.net/lhy_ycu/article/details/40031567 今天来对这23种设计模式做个总结.咱使用设计模式的目的是为了可重用代码.让代 ...
- Java中对象、对象引用、堆、栈、值传递以及引用传递的详解
Java中对象.对象引用.堆.栈.值传递以及引用传递的详解 1.对象和对象引用的差别: (1).对象: 万物皆对象.对象是类的实例. 在Java中new是用来在堆上创建对象用的. 一个对象能够被多个引 ...
- Android解析聚合数据之天气预报
免费天气预报API:https://www.juhe.cn/docs/api/id/73 ,申请APPKEY MainActivity.java <span style="font-s ...
- VC进程间通信之消息传递PostMessge()或SendMessage()
1. 进程内消息: (1). 仅仅传消息码 (2). 传送消息串 发送端: void CTestDlg::OnBnClickedButtonSend() { CString* msg = new C ...
- Linux系统rootpassword改动
重新启动系统. 进入系统引导界面: watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvdTAxMzMzOTg1MQ==/font/5a6L5L2T/fontsi ...
- gulp 静态资源版本控制
package.json { "name": "gulp", "version": "0.0.1", "des ...
- spark on yarn 配置history server
spark在yarn模式下配置history server 1.建立hdfs文件– hadoop fs -mkdir /user/spark– hadoop fs -mkdir /user/spark ...
- 基于IAP和网口升级固件
基于IAP和网口升级固件 一. 需求引入 现有嵌入式设备:基于ARM Cortex-M3处理器.带以太网通讯功能. 为减少设备维护成本节省宝贵的时间和金钱,须要设计网口升级固件功能. 本文描 ...