解题思路
这是一道动态规划的经典题目,主要思路如下:
-
问题分析:
- 给定一个整数数组,可能包含负数
- 求连续子数组的最大和
- 子数组至少包含一个数
-
解决方案:
- 使用动态规划
表示以第
个数结尾的最大子数组和
- 状态转移方程:
- 维护一个全局最大值
代码
#include <iostream>
#include <vector>
#include <sstream>
using namespace std;
int maxSubArray(vector<int>& nums) {
int maxSum = nums[0]; // 全局最大和
int currentSum = nums[0]; // 当前子数组和
for(int i = 1; i < nums.size(); i++) {
// 状态转移:要么加入当前数字,要么重新开始
currentSum = max(nums[i], currentSum + nums[i]);
// 更新全局最大和
maxSum = max(maxSum, currentSum);
}
return maxSum;
}
int main() {
string line;
getline(cin, line);
vector<int> nums;
stringstream ss(line);
int num;
while(ss >> num) {
nums.push_back(num);
}
cout << maxSubArray(nums) << endl;
return 0;
}
import java.util.*;
public class Main {
public static int maxSubArray(int[] nums) {
int maxSum = nums[0];
int currentSum = nums[0];
for(int i = 1; i < nums.length; i++) {
currentSum = Math.max(nums[i], currentSum + nums[i]);
maxSum = Math.max(maxSum, currentSum);
}
return maxSum;
}
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String[] input = sc.nextLine().split(" ");
int[] nums = new int[input.length];
for(int i = 0; i < input.length; i++) {
nums[i] = Integer.parseInt(input[i]);
}
System.out.println(maxSubArray(nums));
}
}
def max_sub_array(nums: list) -> int:
max_sum = nums[0] # 全局最大和
current_sum = nums[0] # 当前子数组和
for i in range(1, len(nums)):
# 状态转移:要么加入当前数字,要么重新开始
current_sum = max(nums[i], current_sum + nums[i])
# 更新全局最大和
max_sum = max(max_sum, current_sum)
return max_sum
def main():
nums = list(map(int, input().split()))
print(max_sub_array(nums))
if __name__ == "__main__":
main()
算法及复杂度
- 算法:动态规划(Kadane算法)
- 时间复杂度:
- 只需要遍历一次数组
- 空间复杂度:
- 只需要常数空间