POJ 2479 Maximum sum (dp)

题意:求序列的两个连续子段的和最大。

题解:dp
l [ ] l[]l[]:保存当前元素之前的最大连续子段和。
r [ ] r[]r[]:保存当前元素之后的最大连续子段和。

#define _CRT_SECURE_NO_WARNINGS
#include<iostream>
#include<cstdio>
#include<string>
#include<cstring>
#include<algorithm>
#include<queue>
#include<stack>
#include<cmath>
#include<vector>
#include<fstream>
#include<set>
#include<map>
#include<sstream>
#include<iomanip>
#define ll long long
using namespace std;

int n, a[55555], t, dp1[55555], dp2[55555], l[55555], r[55555];
struct nnode {
    int l, r, v;
}an[55555];
bool cmp(nnode& a, nnode& b) {
    return a.v > b.v;
}
int main() {
    int i;
    scanf("%d", &t);
    while (t--) {
        scanf("%d", &n);
        for (i = 1; i <= n; i++) {
            scanf("%d", &a[i]);
        }
        memset(l, 0, sizeof(l));
        memset(r, 0, sizeof(r));
        memset(dp1, 0, sizeof(dp1));
        memset(dp2, 0, sizeof(dp2));
        l[0] = -0x3f3f3f3f;
        r[n + 1] = -0x3f3f3f3f;
        for (int i = 1; i <= n; i++) {
            if (dp1[i - 1] > 0) dp1[i] = dp1[i - 1] + a[i];
            else dp1[i] = a[i];
            l[i] = max(dp1[i], l[i - 1]);
        }
        for (int i = n; i >= 1; i--) {
            if (dp2[i + 1] > 0) dp2[i] = dp2[i + 1] + a[i];
            else dp2[i] = a[i];
            r[i] = max(dp2[i], r[i + 1]);
        }
        int ans = -0x3f3f3f3f;
        for (int i = 1; i < n; i++) {
            ans = max(ans, l[i] + r[i + 1]);
        }
        printf("%d\n", ans);
    }
    return 0;
}

版权声明:本文为qq_43680965原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。