-
总时间限制:
- 1000ms 内存限制:
- 65536kB
-
描述
-
Given a set of n integers: A={a1, a2,..., an}, we define a function d(A) as below:
t1 t2 d(A) = max{ ∑ai + ∑aj | 1 <= s1 <= t1 < s2 <= t2 <= n } i=s1 j=s2
Your task is to calculate d(A).
输入
-
The input consists of T(<=30) test cases. The number of test cases (T) is given in the first line of the input.
Each test case contains two lines. The first line is an integer n(2<=n<=50000). The second line contains n integers: a1, a2, ..., an. (|ai| <= 10000).There is an empty line after each case.
输出
- Print exactly one line for each test case. The line should contain the integer d(A). 样例输入
-
1 10 1 -1 2 2 3 -3 4 -4 5 -5
样例输出
-
13
提示
-
In the sample, we choose {2,2,3,-3,4} and {5}, then we can get the answer.
Huge input,scanf is recommended.
-
/* * 1. 从左往右求以i结尾的最大连续子列 dp1[i] = max(dp1[i - 1] + a[i], a[i]); 2. 从右往左以i结尾的最大连续子列 dp2[i] = max(dp2[i + 1] + a[i], a[i]); 3. 通过1求从左往右前i个数 中最大连续子列和 4. 通过2从右往左 后i个数中最大连续子列和 5. 枚举 求 dp1[i] + dp2[i+1]的最大值 */ #include "iostream" #include "cstring" #include "algorithm" using namespace std; int main() { int t; int a[50001]; int dp1[50001]; int dp2[50001]; scanf("%d", &t); while (t--) { int n; scanf("%d", &n); memset(dp1, 0, sizeof(dp1)); memset(dp2, 0, sizeof(dp2)); for (int i = 1; i <= n; i++) scanf("%d", &a[i]); dp1[1] = a[1]; for (int i = 2; i <= n; i++) { dp1[i] = max(dp1[i - 1] + a[i], a[i]); } for (int i = 2; i <= n; i++) { if (dp1[i] < dp1[i - 1]) dp1[i] = dp1[i - 1]; } dp2[n] = a[n]; for (int i = n-1; i >= 1; i--) { dp2[i] = max(dp2[i + 1] + a[i], a[i]); } for (int i = n; i >= 2; i--) { if (dp2[i-1] < dp2[i]) { dp2[i - 1] = dp2[i]; } } int Max = -20002; for (int i = 1; i < n; i++) { if (dp1[i] + dp2[i+1] > Max) Max = dp1[i] + dp2[i+1]; } printf("%d\n", Max); } return 0; }