zoukankan      html  css  js  c++  java
  • 【单调队列】最大子序和

    Tyvj P1305最大子序和

    《进阶指南》单调队列例题

    连续子序和一般转化为前缀和维护, 记为sum数组, 连续的子序列[l, r] 的和即为sum[r] - sum[l - 1] 

    原问题转化为 找到两个位置l, r , 使得sum[l] - sum[r] 最大 且 r - l <= m。

    所以单调队列维护一个下标递增, 前缀和也递增的序列, ans不断更新

     1 #include<cstdio>
     2 #include<iostream>
     3 using namespace std;
     4 const int sz = 300030;
     5 int n, m, ans;
     6 int a[sz], sum[sz], p[sz], q[sz];
     7 void work() {
     8     int head = 1, tail = 0;
     9     q[1] = 0;
    10     for(int i = 1; i <= n; i++) {
    11         while(head <= tail && p[head] < i - m) head++;
    12         ans = max(ans, sum[i] - sum[p[head]]);
    13         while(head <= tail && sum[i] <= sum[p[tail]]) tail--;
    14 //        q[++tail] = sum[i];
    15         p[++tail] = i;
    16 //        while(p[head] < i - m) head++;
    17     }
    18     printf("%d", ans);
    19 }
    20 int main() {
    21     scanf("%d%d", &n, &m);
    22     for(int i = 1; i <= n; i++) {
    23         scanf("%d", &a[i]);
    24         sum[i] = a[i] + sum[i-1];
    25     }
    26     work();
    27     return 0;
    28 }
  • 相关阅读:
    自学java--5
    自学java--4
    自学java--3
    自学java--2
    自学java--1
    java中的IO操作---File类
    TCP/UDP编程实例
    什么是服务端与客户端详解
    【提高组】并查集
    【ToDoList】自己选择的路跪着也要走下去
  • 原文地址:https://www.cnblogs.com/Hwjia/p/9885467.html
Copyright © 2011-2022 走看看