「动态规划」如何求最大子数组和?如何求环形子数组的最大和?

53. 最大子数组和icon-default.png?t=N7T8https://leetcode.cn/problems/maximum-subarray/description/

给你一个整数数组nums,请你找出一个具有最大和的连续子数组(子数组最少包含一个元素),返回其最大和。子数组是数组中的一个连续部分。

  1. 输入:nums = [-2,1,-3,4,-1,2,1,-5,4],输出:6,解释:连续子数组[4,-1,2,1]的和最大,为6。
  2. 输入:nums = [1],输出:1。
  3. 输入:nums = [5,4,-1,7,8],输出:23。

提示:1 <= nums.length <= 10^5,-10^4 <= nums[i] <= 10^4。


我们用动态规划的思想来解决这个问题。

确定状态表示:根据经验和题目要求,我们用dp[i]表示:以i位置为结尾的子数组中的最大和。比如,dp[3]就表示:下标范围是[0, 3],[1, 3],[2, 3],[3, 3]这4个子数组中的最大和。

推导状态转移方程:考虑dp[i],

  • 如果子数组的长度是1,只有下标范围是[i, i]的子数组符合条件,此时的子数组和是nums[i]。
  • 如果子数组的长度大于1,那么以i位置为结尾的子数组中的最大和,就等于以i - 1位置为结尾的子数组中的最大和加上nums[i],即dp[i - 1] + nums[i]。

dp[i]取上面2种情况的较大值,即dp[i] = max(nums[i], dp[i - 1] + nums[i])

初始化:根据状态转移方程,我们需要初始化dp[0]的值。本题中,既可以根据状态表示直接初始化dp[0] = nums[0];也可以在最前面加上一个辅助结点dp[0] = 0,这样max(num[0], dp[0] + nums[0]) = max(nums[0], 0 + nums[0]) = nums[0],和前一种初始化方式等价。这里我们选择后一种方式。

填表顺序:根据状态转移方程,dp[i]依赖于dp[i - 1],所以应从左往右填表

返回值:由于我们并不确定子数组的结尾是那个位置,根据状态表示,我们应返回整个dp表除了辅助结点之外的最大值

细节问题:假设nums有n个元素。由于新增了一个辅助结点,所以dp表的规模是1 x (n + 1),且下标的映射关系为:dp[i]对应nums[i - 1]

时间复杂度:O(N),空间复杂度:O(N)。

class Solution {
public:int maxSubArray(vector<int>& nums) {int n = nums.size();// 创建dp表vector<int> dp(n + 1);// 填表for (int i = 1; i <= n; i++) {dp[i] = max(nums[i - 1], dp[i - 1] + nums[i - 1]);}// 返回结果return *max_element(dp.begin() + 1, dp.end());}
};

918. 环形子数组的最大和icon-default.png?t=N7T8https://leetcode.cn/problems/maximum-sum-circular-subarray/description/给定一个长度为n的环形整数数组nums,返回nums的非空子数组的最大可能和。环形数组意味着数组的末端将会与开头相连呈环状。形式上,nums[i]的下一个元素是nums[(i + 1) % n],nums[i]的前一个元素是nums[(i - 1 + n) % n]。子数组最多只能包含固定缓冲区nums中的每个元素一次。形式上,对于子数组nums[i],nums[i + 1],……,nums[j],不存在i <= k1,k2 <= j其中k1 % n == k2 % n。

  1. 输入:nums = [1,-2,3,-2],输出:3,解释:从子数组[3]得到最大和3。
  2. 输入:nums = [5,-3,5],输出:10,解释:从子数组[5,5]得到最大和5 + 5 = 10。
  3. 输入:nums = [3,-2,2,-3],输出:3,解释:从子数组[3]和[3,-2,2]都可以得到最大和3。

提示:n == nums.length,1 <= n <= 3 * 10^4,-3 * 10^4 <= nums[i] <= 3 * 10^4。


环形子数组分为2种情况:

  • 环形子数组不包含首尾相连的部分,也就是说,环形子数组整体位于数组的中央。此时的最大和就是上题中的最大子数组和
  • 环形子数组包含首尾相连的部分,也就是说,环形子数组位于数组的左右两端。此时的最大和等于整个数组的和减去最小子数组和,最小子数组和的求法和上题中的最大子数组和完全类似。

也就是说,只需要求出最大子数组和fmax、最小子数组和gmin以及整个数组的和sum,本题的答案就是max(fmax, sum - gmin)

其中,最小子数组和的求法也是按照上题中动态规划的思路,只需要把状态转移方程中的max改为min,返回结果也从返回最大值改为返回最小值

这里需要注意一个细节问题,如果最终算出来的最小子数组和gmin,整个数组的和sum,满足gmin = sum,此时的sum - gmin = 0,并不表示包含首尾相连部分的环形子数组的最小和是0,因为此时gmin = sum说明最小子数组和是所有元素的和,那么从整个数组中去掉最小子数组和包含的元素后,就啥也不剩了,但是环形子数组中至少包含1个元素,所以这种情况要单独处理一下,如果算出来sum = gmin,那么最终结果就不是max(fmax, sum - gmin),而是直接返回fmax

我们可以用accumulate、max_element和min_element分别完成求和、求最大值、求最小值的操作,也可以在一个循环内手动完成。这里我们选择在一个循环内同时填2个表、求最大值、求最小值以及求和。其中,f表用来求最大子数组和,g表用来求最小子数组和。

时间复杂度:O(N),空间复杂度:O(N)。

class Solution {
public:int maxSubarraySumCircular(vector<int>& nums) {int n = nums.size(), sum = 0, fmax = INT_MIN, gmin = INT_MAX;// 创建dp表vector<int> f(n + 1);auto g = f;// 填表for (int i = 1; i <= n; i++) {int x = nums[i - 1];f[i] = max(x, f[i - 1] + x);g[i] = min(x, g[i - 1] + x);fmax = max(fmax, f[i]);gmin = min(gmin, g[i]);sum += x;}// 返回结果return gmin == sum ? fmax : max(fmax, sum - gmin);}
};

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/1452061.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

Studio One软件最新版下载及详细安装教程

Studio One 6是一款功能丰富、专业级的音乐制作软件&#xff0c;它具备灵活的工作流程和高效的团队协作能力&#xff0c;能帮助用户实现高质量的音乐创作和制作。 智能模板更快的启动&#xff0c;全新的智能模板为你手头的任务提供了必要的工具集&#xff0c;包括基本录制、混音…

这世上又多了一只爬虫(spiderflow)

让我们一起默念&#xff1a; 爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫爬虫 接着大声喊出来&#xff1a; 一&#xff01;只&#xff01;爬&#xff01;虫&#xff01;呀&#xff01;爬&#xff01;呀&#xff01;爬&#xf…

HTMLCSS详细总结(提高版)

HTML5的新特性 1. HTML5 新增的语义化标签 <div class“header”> </div> <div class“nav”> </div> <div class“content”> </div> <div class“footer”> </div> <header>&#xff1a;头部标签<nav>&#…

教师人才引进需要什么条件

在这个竞争激烈的时代&#xff0c;学校和教育机构都在寻求优秀的教育工作者&#xff0c;以提升教学口碑和学生的学习体验。而引进教师人才可并非易事&#xff0c;涉及到多方面的考量。 专业素养。一个优秀的教师需要具备扎实的专业知识和教育理论&#xff0c;能够不断更新自己的…

【算法专题--链表】反转链表II--高频面试题(图文详解,小白一看就会!!!)

目录 一、前言 二、题目描述 三、解题方法 ⭐迭代法 --- 带哨兵位&#xff08;头节点&#xff09; &#x1f95d; 什么是哨兵位头节点&#xff1f; &#x1f34d; 解题思路 四、总结与提炼 五、共勉 一、前言 反转链表II这道题&#xff0c;可以说是--链表专题--&am…

深入学习Java `synchronized` 关键字

深入学习Java synchronized 关键字 synchronized关键字通过确保在同一时间只有一个线程可以执行某个代码块&#xff0c;从而防止多个线程同时访问共享资源时发生数据不一致的问题。 修饰方法 当synchronized用于修饰实例方法时&#xff0c;表示当前实例对象是同步锁。这意味…

内网安全【2】-域防火墙

1.判断什么时候用代理 2.判断什么时候用隧道 3.判断出网和不出网协议 4.如何使用代理建立节点并连接 5.如何使用隧道技术封装协议上线 6.判断哪些代理或隧道情况选择放弃 代理技术&#xff1a;解决网络通讯不通的问题(利用跳板机建立节点后续操作)&#xff08;网络设置导…

操作系统复习-线程同步

互斥量 两个线程的指令交叉执行互斥量可以保证先后执行称为原子性 原子性是指一系列操作不可被中断的特性这一系列操作要么全部执行完成&#xff0c;要么全部没有执行不存在部分执行部分未执行的情况 互斥锁 互斥量是最简单的线程同步的方法互斥锁&#xff0c;处于两态之一的…

el-table表头文字换行或者修改字体颜色样式

例如 <el-table:data"tableData":header-cell-style"headClass" style"width: 100%;" border ><el-table-columnprop"address"label"生产工序"align"center"></el-table-column> //重点看这里…

经典的带环链表问题(链表补充)

环形链表1 运用快慢指针的方法&#xff0c;fast ,slow从头节点出发&#xff0c;快指针走两步&#xff0c;慢指针走一步&#xff0c;若有环&#xff0c;快指针先进环&#xff0c;后续如果慢指针和快指针相遇&#xff0c;则链表带环。转换成了追击问题。 struct ListNode {int v…

誉天5月红帽战报:恭喜14名学员通过RHCE认证,通过率87.5%!

红帽认证是全球公认的Linux权威认证之一&#xff0c;对于Linux从业者来说具有很高的价值和认可度。旨在评估考生在Linux系统管理和应用方面的专业知识和技能。红帽考试是Linux从业者提升自身技能水平和职业竞争力的重要途径之一。 5月份&#xff0c;誉天14名学员通过了RHCE认证…

Flask快速入门2(请求扩展、CBV装饰器、闪现、g对象、蓝图、wtforms)

Flask快速入门 目录 Flask快速入门请求扩展before_requestafter_requestteardown_requesterrorhandler CBV加装饰器闪现(Flash)示例 g对象蓝图(blueprint)wtforms 请求扩展 常用的请求扩展&#xff1a; before_requestafter_requestteardown_requesterrorhandler before_req…

Stable-Diffusion-WebUI 常用提示词插件

SixGod提示词插件 SixGod提示词插件可以帮助用户快速生成逼真、有创意的图像。其中包含&#xff0c;清空正向提示词”和“清空负向提示词、提示词起手式包含人物、服饰、人物发型等各个维度的提示词、一键清除正面提示词与负面提示词、随机灵感关键词、提示词分类组合随机、动…

【GD32F303红枫派使用手册】第十六节 USART-DMA串口收发实验

16.1 实验内容 通过本实验主要学习以下内容&#xff1a; 串口DMA工作原理 使用DMA进行串口收发 16.2 实验原理 16.2.1 串口DMA工作原理 在前面ADC章节中&#xff0c;我们介绍了DMA的工作原理&#xff0c;这里就不多做介绍。从GD32F303用户手册中可以查到&#xff0c;各串…

四轴飞行器、无人机(STM32、NRF24L01)

一、简介 此电路由STM32为主控芯片&#xff0c;NRF24L01、MPU6050为辅,当接受到信号时&#xff0c;处理对应的指令。 二、实物图 三、部分代码 void FlightPidControl(float dt) { volatile static uint8_t statusWAITING_1; switch(status) { case WAITING_1: //等待解锁 if…

波卡近期活动一览| Polkadot Decoded 2024 重磅来袭,300 万 DOT 将用于 DeFi 增长

Polkadot 生态近期活动精彩纷呈&#xff0c;线上线下火热进行中&#xff01;此外&#xff0c;Polkadot 2.0 的关键升级即将到来&#xff0c;Gavin Wood 博士也将在最新访谈节目中分享更多关于波卡的未来发展蓝图。波卡 DAO 通过提案&#xff0c;分配 300 万 DOT 支持 DeFi 生态…

12.容器间的互联(--link 是单方向的!!!)

容器间的互联&#xff08;–link 是单方向的&#xff01;&#xff01;&#xff01;&#xff09; –link意思就是链接容器进行通信 用法&#xff1a;--link 容器名字:随意设置别名&#xff1b;例如&#xff1a;--link nginx:nginx 注释&#xff1a;同一个容器中&#xff0c;可…

动态功能连接评估方法的变异性

摘要 背景&#xff1a;动态功能连接(dFC)已成为理解大脑功能的一种重要测量指标。虽然已经开发了各种各样的方法来评估dFC&#xff0c;但目前尚不清楚方法的选择会如何影响结果。在这里&#xff0c;本研究旨在考察常用dFC方法的结果变异性。 方法&#xff1a;本研究在Python中…

公司面试题总结(六)

31.说一说 webpack 的构建流程是什么&#xff1f; ⚫ 初始化流程&#xff1a; ◼ 从配置文件和 Shell 语句中读取与合并参数 ◼ 初始化需要使用的插件和配置插件等执行环境所需要的参数 ⚫ 编译构建流程&#xff1a; ◼ 从 Entry 发出&#xff0c;针对每个 Module 串行…

仙侠手游【天道情缘】修复版服务端+GM后台+详细教程

下载地址&#xff1a;仙侠手游【天道情缘】修复版服务端GM后台详细教程