最大连续子序列和,最大连续子序列乘
这个问题很常见了,只要找到最优子结构就好办了
最优子结构为
max[i] = Math.max(max[i-1] + num[i], num[i])
其中max[i]为以第i个元素为右边界的子数组的最大值,num为输入的int数组
下面给出解法
public int maxSumArray(int[] num) {
int max;
if (num[0] > 0) {
max = num[0];
} else {
max = 0;
}
int[] count = new int[num.length];
count[0] = num[0];
for (int i = 1; i < num.length; ++i) {
count[i] = (count[i - 1] + num[i] > num[i]) ? (count[i - 1] + num[i]) : num[i];
if (max < count[i]) {
max = count[i];
}
}
return max;
}
其实,可以不用count数组,而只用一个count变量记录以左边元素为界的最大值即可,改写后如下
public int maxSumArray(int[] num) {
int max = num[0];
int count = num[0];
for (int i = 1; i < num.length; ++i) {
count = Math.max(count+num[i], num[i]);
if (max < count) {
max = count;
}
}
return max;
}
上面的问题是找到最大连续子序列和,还有一个类似的问题是最大连续子序列乘,就是找到一个连续的子序列,使这个子序列的连乘最大
比如,数组[2,6,-5,8]的最大连续子序列乘是12,就是2*6
这个问题的最优子结构为
f(k) = max( f(k-1) * A[k], A[k], g(k-1) * A[k] )
g(k) = min( g(k-1) * A[k], A[k], f(k-1) * A[k] )
f(k)表示,以第k个元素为结尾的子序列连乘的最大值
g(k)表示,以第k个元素为结尾的子序列连乘的最小值
代码如下
public int maxProduct(int[] A) {
if (A == null || A.length == 0) {
return 0;
}
int result = A[0];
int max = A[0];
int min = A[0];
for (int i = 1; i < A.length; ++i) {
int tmp = max;
max = Math.max(Math.max(max*A[i], min*A[i]), A[i]);
min = Math.min(Math.min(tmp*A[i], min*A[i]), A[i]);
if (result < max) {
result = max;
}
}
return result;
}
代码很好理解了

浙公网安备 33010602011771号