zoukankan      html  css  js  c++  java
  • SPOJ GSS2 Can you answer these queries II

    Can you answer these queries II

    Time Limit: 1000ms
    Memory Limit: 262144KB
    This problem will be judged on SPOJ. Original ID: GSS2
    64-bit integer IO format: %lld      Java class name: Main
     

    Being a completist and a simplist, kid Yang Zhe cannot solve but get Wrong Answer from most of the OI problems. And he refuse to write two program of same kind at all. So he always failes in contests.

    When having a contest, Yang Zhe looks at the score of every problems first. For the problems of the same score, Yang Zhe will do only one of them. If he's lucky enough, he can get all the scores wanted.

    Amber is going to hold a contest in SPOJ. She has made a list of N candidate problems, which fit Yang Zhe very well. So Yang Zhe can solve any problem he want. Amber lined up the problems, began to select. She will select a subsequence of the list as the final problems. Being A girl of great compassion, she'd like to select such a subsequence (can be empty) that Yang Zhe will get the maximal score over all the possible subsequences.

    Amber found the subsequence easily after a few minutes. To make things harder, Amber decided that, Yang Zhe can take this contest only if Yang Zhe can answer her Q questions. The question is: if the final problems are limited to be a subsequence of list[X..Y] (1 <= X <= Y <= N), what's the maximal possible score Yang Zhe can get?

    As we know, Yang Zhe is a bit idiot (so why did he solve the problem with a negative score?), he got Wrong Answer again... Tell him the correct answer!

    Input

    • Line 1: integer N (1 <= N <= 100000);
    • Line 2: N integers denoting the score of each problem, each of them is a integer in range [-100000, 100000];
    • Line 3: integer Q (1 <= Q <= 100000);
    • Line 3+i (1 <= i <= Q): two integers X and Y denoting the ith question.

    Output

    • Line i: a single integer, the answer to the ith question.

    Example

    Input:
    9
    4 -2 -2 3 -1 -4 2 2 -6
    3
    1 2
    1 5
    4 9
    
    Output:
    4
    5
    3
    
    
    Warning: large input/output data,be careful with certain languages
     

    Source

     
    解题:非常尤其特别厉害的线段树
    假设没有重复的数据,那么

    $s[1] = a[1] + a[2] + a[3] + ... + a[i];$
    $s[2] = a[2] + a[3] + ... + a[i];$

    $s[3] = a[3] + ... + a[i];$

    $s[i] = a[i];$

    也就是说,线段树上的每个叶子代表的是s[x]

    我们说假设这个是后缀和,但是,我们要前缀和,所以在做lazy标记的时间做了手脚,只把最大的lazy下传去修改最大子段和

    $ss[1] = max( a[1] + a[2]  + ... + a[k_1] ) (    k_1leq i );$

    $ss[2] = max( a[2] + a[3] + ...+ a[k_2] )  (    k_2leq i );$

    我们可以求的是以i为右端点的询问,就是 $ss[l] ....ss[r]( r == i )$ 中的最大值;

    这样子就是维护了前缀和,既有前缀和,也有后缀和,答案自然就出来了

    问题是有重复的怎么办?只要记录每个元素上次出现位置,然后把上次出现的位置+1到当前位置这一段加上当前元素就是了,这样保证每个s[i]里面最多只加入了该元素一次

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 typedef long long LL;
     4 const int maxn = 100010;
     5 struct node{
     6     int lt,rt;
     7     LL lazy,sum,maxlazy,maxsum;
     8 }tree[maxn<<2];
     9 struct QU{
    10     int x,y,id;
    11     bool operator<(const QU &rhs)const{
    12         return y < rhs.y;
    13     }
    14 }q[maxn];
    15 void build(int lt,int rt,int v){
    16     tree[v].lt = lt;
    17     tree[v].rt = rt;
    18     tree[v].sum = tree[v].maxsum = 0;
    19     tree[v].lazy = tree[v].maxlazy = 0;
    20     if(lt == rt) return;
    21     int mid = (lt + rt)>>1;
    22     build(lt,mid,v<<1);
    23     build(mid + 1,rt,v<<1|1);
    24 }
    25 void _set(int x,int y){
    26     tree[x].maxlazy = max(tree[x].maxlazy,tree[x].lazy + tree[y].lazy);
    27     tree[x].maxsum = max(tree[x].maxsum,tree[x].sum + tree[x].maxlazy);
    28     tree[x].lazy += tree[y].lazy;
    29     tree[x].sum += tree[x].lazy;
    30 }
    31 void pushdown(int v){
    32     if(tree[v].lazy || tree[v].maxlazy){
    33         _set(v<<1,v);
    34         _set(v<<1|1,v);
    35         tree[v].lazy = tree[v].maxlazy = 0;
    36     }
    37 }
    38 void pushup(int v){
    39     tree[v].sum = max(tree[v<<1].sum,tree[v<<1|1].sum);
    40     tree[v].maxsum = max(tree[v<<1].maxsum,tree[v<<1|1].maxsum);
    41 }
    42 void update(int lt,int rt,int val,int v){
    43     if(lt <= tree[v].lt && rt >= tree[v].rt){
    44         tree[v].lazy += val;
    45         tree[v].sum += val;
    46         tree[v].maxlazy = max(tree[v].maxlazy,tree[v].lazy);
    47         tree[v].maxsum = max(tree[v].maxsum,tree[v].sum);
    48         return;
    49     }
    50     pushdown(v);
    51     if(lt <= tree[v<<1].rt) update(lt,rt,val,v<<1);
    52     if(rt >= tree[v<<1|1].lt) update(lt,rt,val,v<<1|1);
    53     pushup(v);
    54 }
    55 LL query(int lt,int rt,int v){
    56     if(lt <= tree[v].lt && rt >= tree[v].rt) return tree[v].maxsum;
    57     pushdown(v);
    58     if(rt <= tree[v<<1].rt) return query(lt,rt,v<<1);
    59     if(lt >= tree[v<<1|1].lt) return query(lt,rt,v<<1|1);
    60     return max(query(lt,rt,v<<1),query(lt,rt,v<<1|1));
    61 }
    62 int pre[maxn<<2],a[maxn],n,m;
    63 LL ans[maxn];
    64 int main(){
    65     while(~scanf("%d",&n)){
    66         memset(pre,0,sizeof pre);
    67         for(int i = 1; i <= n; ++i)
    68             scanf("%d",a + i);
    69         scanf("%d",&m);
    70         for(int i = 0; i < m; ++i){
    71             scanf("%d%d",&q[i].x,&q[i].y);
    72             q[i].id = i;
    73         }
    74         sort(q,q + m);
    75         build(1,n,1);
    76         for(int i = 1,j = 0; i <= n; ++i){
    77             update(pre[a[i] + maxn] + 1,i,a[i],1);
    78             pre[a[i] + maxn] = i;
    79             while(j < m && q[j].y == i){
    80                 ans[q[j].id] = max(0LL,query(q[j].x,q[j].y,1));
    81                 ++j;
    82             }
    83         }
    84         for(int i = 0; i < m; ++i) printf("%lld
    ",ans[i]);
    85     }
    86     return 0;
    87 }
    View Code
  • 相关阅读:
    mysql锁表与解锁
    问题汇总
    安装一台Centos7桌面版的跳板机
    Centos7二进制部署k8s-v1.20.2 ipvs版本(部署mysql、nacos)
    Centos7二进制部署k8s-v1.20.2 ipvs版本(Prometheus监控k8s)
    CV2 安装异常
    PostgreSQL VACUUM 没有效果(无法清理死元组)的原因
    SQL Server 进程运行状态解析
    mysql 几种启动和关闭mysql服务的方法和区别
    MySQL学习(九)小结(转载)
  • 原文地址:https://www.cnblogs.com/crackpotisback/p/4887970.html
Copyright © 2011-2022 走看看