算法题:剑指 Offer 42. 连续子数组的最大和(题目+思路+代码+注释)时空 O(N) O(1) 0ms击败98%、72%用户
题目
剑指 Offer 42. 连续子数组的最大和
输入一个整型数组,数组中的一个或连续多个整数组成一个子数组。求所有子数组的和的最大值。
要求时间复杂度为O(n)。
示例1:
输入: nums = [-2,1,-3,4,-1,2,1,-5,4]
输出: 6
解释: 连续子数组 [4,-1,2,1] 的和最大,为 6。
提示:
1 <= arr.length <= 10^5
-100 <= arr[i] <= 100
注意:本题与主站 53 题相同:https://leetcode-cn.com/problems/maximum-subarray/
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/lian-xu-zi-shu-zu-de-zui-da-he-lcof
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
思路
既然要时间复杂度O(n),只能循环一次,那么其实我们可以知道,我求当前的最大子数组和必定和前面一个的和有必然联系,那么我们这样想,从第一个开始,我以当前数作为最小子数组的末尾值,那么当前的最大值就是自己,而下一个的计算肯定就是Max(当前值,当前值+前面的子数组最大值),这样状态转移方程就出来了
f(i) = max(f(i),f(i)+f(i-1))
于是就可以轻松写下如下代码,秒过。
代码
package leetcode.offer.q42;
public class Solution {
public int maxSubArray(int[] nums) {
int[] maxSums = new int[nums.length];
maxSums[0] = nums[0];
int max = maxSums[0];
for (int i = 1,len = nums.length; i < len;i++){
if (maxSums[i-1] > 0){
//前面的能让我增加
maxSums[i] = maxSums[i-1] + nums[i];
}else {
//前面的让我更小了我还不如就我自己
maxSums[i] = nums[i];
}
if (maxSums[i] > max){
max = maxSums[i];
}
}
return max;
}
public static void main(String[] args) {
int[] nums = {-2,1,-3,4,-1,2,1,-5,4};
System.out.println(new Solution().maxSubArray(nums));
}
}
本文来自博客园,作者:HumorChen99,转载请注明原文链接:https://www.cnblogs.com/HumorChen/p/18039535
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· 从HTTP原因短语缺失研究HTTP/2和HTTP/3的设计差异
· 三行代码完成国际化适配,妙~啊~