01-最大子列和问题
最大子列和问题
概述
本文主要讲解最大子列和问题的求解
什么是最大子列和问题?有一个整数数组{A1, A2,A3,...,An}
求函数f(i,j)=max(0,∑Ak), k∈[i,j]
的值
简单来说,求一个数组所有子序列中和最大的子序列的和的值
方法
简单来说有四种解决方法,分别为三重循环,二重循环,分治法,单循环
package com.kuang.example01;
/**
* 求最大子列的和
* 最大子列和问题,有一个整数序列{A1,A2,A3,A4...An}
* 求f(i,j)=max{0, ∑Ak} k从i取到j
* 简单来说就是求一个序列的最大的子列和
*
* @since 2022-09-19
*/
public class MaxSumOfSubSequence {
/**
* 使用三重循环 时间复杂度O(n^3)
*
* @param a
* @return
*/
public int threeFor(int[] a){
int curSum = 0;
int maxSum = 0;
for (int i = 0; i < a.length; i++) {
for (int j = i; j < a.length; j++) {
curSum = 0;
for (int k = i; k <j ; k++) {
curSum += a[k];
}
if(curSum>maxSum){
maxSum = curSum;
}
}
}
return maxSum;
}
/**
* 使用二重循环 时间复杂度O(n^2)
*
* @param a
* @return
*/
public int twoFor(int[] a){
int curSum = 0;
int maxSum = 0;
for (int i = 0; i < a.length; i++) {
curSum = 0;
for (int j = i; j < a.length; j++) {
curSum += a[j];
if(curSum>maxSum){
maxSum = curSum;
}
}
}
return maxSum;
}
/**
* 使用分治法 时间复杂度O(nlog(n))
*
* @param a
* @return
*/
public int divideAndConquer(int[] a){
// 分治写不出来,以后再写
return 0;
}
/**
* 使用单循环 时间复杂度O(n)
*
* @param a
* @return
*/
public int oneFor(int[] a){
int curSum = 0;
int maxSum = 0;
for (int i = 0; i < a.length; i++) {
curSum += a[i];
if (curSum>maxSum){
maxSum = curSum;
}
if(curSum<0){
curSum =0;
}
}
return maxSum;
}
public static void main(String[] args) {
int[] a = {-1,3,-2,4,-6,1,6,-1}; //正确结果应该是7
MaxSumOfSubSequence sum = new MaxSumOfSubSequence();
int result = sum.oneFor(a);
System.out.println(result);
int[] a1 = {4,-3,5,-2,-1,2,6,-2}; //正确结果应该是11
int result1 = sum.oneFor(a1);
System.out.println(result1);
}
}