穷举,确定好子数组的开始与结束
public int maxSubArray(int[] nums){ int sum = 0, max = 0, start = 0, end = 0; for(int i = 0, len = nums.length;i < len;i ++){ for(int j = i; j < len;j ++){ sum = 0; for(int k = i;k <= j;k ++){ sum += nums[k]; } if(sum > max){ max = sum; start = i; end = j; } } } System.out.println(start + "==" + end); return max; }
动态规划
public int maxSubArray(int[] nums){ int sum = 0, max = nums[0]; for(int i = 0, len = nums.length;i < len;i ++){ sum += nums[i]; if(sum > max){ max = sum; } if(sum < 0){ sum = 0; } } return max; }
/* * MaxSum.cpp * * Created on: 2014-5-6 * Author: wangzhu */ #include<cstdio> #include<iostream> using namespace std; #define LL long long #define NMAX 10001 int num[NMAX]; void solve1() { int t, start, end, first; LL sum, nmax; while (~scanf("%d", &t) && t) { for (int i = 0; i < t; i++) { scanf("%d", num + i); } //first:记录最大连续子序列和的第一个数的位置, start:记录最大连续子序列和的第一个数的位置 end:记录最大连续子序列和的最后一个数的位置 first = start = end = 0; //sum:记录连续子序列的和 nmax:记录最大连续子序列的和 sum = nmax = num[0]; for (int i = 1; i < t; i++) { if (sum < 0) { //若和小于0,则更新子序列和,以及开始记录位置 sum = num[i]; first = i; } else { //反之,则继续加 sum += num[i]; } if (sum > nmax) { //当前子序列和大于最大子序列和时,更新最大自序列和,并该序列的更新起始位置 nmax = sum; start = first; end = i; } } if (nmax < 0) { nmax = 0; start = 0, end = t - 1; } printf("%lld %d %d ", nmax, num[start], num[end]); } } void solve2() { int t, start, end; LL sum[NMAX], nsum; while (~scanf("%d", &t) && t) { for (int i = 0; i < t; i++) { scanf("%d", num + i); } sum[0] = num[0]; for (int i = 1; i < t; i++) { if (sum[i - 1] > 0) { sum[i] = sum[i - 1] + num[i]; } else { sum[i] = num[i]; } } end = 0; nsum = sum[0]; for (int i = 1; i < t; i++) { if (sum[i] > nsum) { nsum = sum[i]; end = i; } } if (nsum < 0) { nsum = 0, start = 0, end = t - 1; } else { start = end; for (int i = end - 1; i >= 0; i--) { if (sum[i] >= 0) { start = i; } else { break; } } } printf("%lld %d %d ", nsum, num[start], num[end]); } } int main() { // freopen("data.in", "r", stdin); solve2(); return 0; }