最大连续子列
From: LeetCode53.
Given an integer array nums, find the contiguous subarray (containing at least one number) which has the largest sum and return its sum.
Example:
Input: [-2,1,-3,4,-1,2,1,-5,4],
Output: 6
Explanation: [4,-1,2,1] has the largest sum = 6.
设置两个变量,一个记录当前连加的值,另一个记录目前位置最大连续子序列,迭代更新。
int MaxSubArray(const vector<int>& arr)
{
int max_so_far = INT_MIN;
int sum = 0;
for (int e : arr)
{
if (sum > 0)
sum += e;
else
sum = e;
max_so_far = max(max_so_far, sum);
}
return max_so_far;
}思路二
上面的方法,其实算是贪心法。从前往后累加,遇到 sum < 0 就丢掉,重新开始累加,因为不丢掉肯定给最终的子数组的和带来负作用。其实这题还可以用动态规划的思想来做(EPI例题)。想要知道数组 A[n] 的最大子数组的和,如果知道 A[n-1] 的最大子数组的和会否有帮助呢?答案是不会。记 ,特别的,记 . 如果我们知道所有子数组 A[0:i], i ⇐ n-1 的最小和,那么用 和它作差就得到了 A[n-1] 的最大子数组和。同理 A[n] 也一样。
代码选自EPI,
int FindMaximumSubarray(const vector<int>& A) {
int min_sum = 0, sum = 0, max_sum = 0;
for (int i = 0; i < A.size(); ++i) {
sum += A[i];
if (sum < min_sum) {
min_sum = sum;
}
if (sum - min_sum > max_sum) {
max_sum = sum - min_sum;
}
}
return max_sum;
}类似的,动态规划模板思路。代码来自姚老师,
public int maxSubArray(int[] nums) {
int n = nums.length;
int[] fMax = new int[n+1]; // 每一个元素都是以当前元素为结尾的子数组,这个子数组对应的和
int res = Integer.MIN_VALUE;
for (int i = 0; i < n; i++) {
fMax[i+1] = Math.max(fMax[i], 0) + nums[i]; //得到以x结尾的最大子数组和
res = Math.max(res, fMax[i+1]);
}
return res;
}