算法设计与分析[0009] Dynamic Programming(II)(Maximum Sum/Product Subarray)
时间:2019-08-25
本文章向大家介绍算法设计与分析[0009] Dynamic Programming(II)(Maximum Sum/Product Subarray),主要包括算法设计与分析[0009] Dynamic Programming(II)(Maximum Sum/Product Subarray)使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。
原文引用https://www.dazhuanlan.com/2019/08/25/5d625b5c4d1ea/
本文通过 53. Maximum Subarray & 152. Maximum Product Subarray 分析根据动态规划思路进行问题求解中的一个关键环节:子问题的拆分和求解。
Problem Description
- 两道题解决的问题相似,都是求解给定序列中满足某种数学特征(和最大/乘积最大)的子序列,虽然不需要将该子序列输出。
- 留意的关键字眼是:
containing at least one number
,所以给定序列至少有一个元素,这也启发我们可以将其作为特殊处理。
53. Maximum Subarray 解题思路
- 思路一:$sums[j]$ 为序列前 j 个元素的最大子段和作为求解的子问题,则 $sum[n]$ 则为问题的答案。然而,如何利用 $sums[1, 2, …, j-1]$ 对 $sums[j]$ 进行求解呢?显然需要知道前 j 个元素的最大字段和的子段起始和终止位置,求解这个子问题的状态迁移显然比较复杂。
- 换一种思路。思路二:$sums[j]$ 为以第 j 个元素为结尾的子段的最大子段和作为求解的子问题,$max_{1 leq j leq n}(sums[j])$ 即为整个序列的最大子段和。而通过 $sums[j-1]$ 和当前元素 $nums[j]$ 即可计算以第 j 个元素为结尾的最大子段和 $sums[j]$,
状态转移方程
如下:
$$ sums[j+1] = begin{cases} nums[j+1] sums[j] lt 0 cr sums[j] + nums[j+1] others end{cases}$$ - 根据思路二,53. Maximum Subarray 解答如下:
1 |
class { |
- 为了得到
largestSum
对应的子序列,我们可以通过变量startIdx
记录以第 j 个元素结尾(endIdx
)的最大子段和对应子序列的起始位置,$nums[startIdx, …, endIdx]$ 即为对应的子序列;另外,考虑到当前状态只与前一个状态有关,所以可以使用变量代替数组,节省内存,同时,避免获取The largest sum of the whole array
时的重复循环。
1 |
class Solution { |
152. Maximum Product Subarray 解题思路
- 这一题的解题流程与上一题基本类似,但是要解决的关键问题是:状态转移,即如何根据上一个子问题(以第 j 个元素为结尾的子段的max product)的答案推算出当前子问题的结果。
- 从上一题的分析可以看出,当前子问题(以第 j 个元素为结尾的子段的max sum)的计算只需考虑上一个子问题的结果 $sum[j-1]$,$sum[j-1] < 0$,因为是加法,显然可以将子问题结果忽略;$sum[j-1] > 0$,$sum[j-1]$ 加上当前元素就是当前子问题的结果。
- 类似的问题,只不过换成乘积,子问题的求解就变得复杂了,需要考虑以下几种情况:
- 当前元素是正数,max product可能是正正得正的情况,因为都是整数,乘积>1,上一子问题的结果乘上当前元素即为当前子问题的答案
- 当前元素是负数,max product可能是负负得正的情况,因此需要维护以第 j 个元素为结尾的子段的min product(很大可能是负数)
- 另外,需要考虑上一个子问题的结果为0的情况
- 总之,乘积的最大值为上述三种情况之一
状态转移方程如下:
$$ maxProducts[j+1] = max(maxProducts[j-1]*nums[j], minProducts[j-1]*nums[j], nums[j])$$
- 152. Maximum Product Subarray 解答如下:
1 |
class Solution { |
- 与上一题类似,添加额外变量,也能实现节省内存,记录子段最大乘积对应子段($nums[startIdx, endIdx]$)的起始和终止位置。
1 |
class Solution { |
原文地址:https://www.cnblogs.com/petewell/p/11408859.html
- R语言数据清洗实战——复杂数据结构与list解析
- R语言爬虫实战——知乎live课程数据爬取实战
- Python爬虫系列(二)Quotes to Scrape(谚语网站的爬取实战)
- R语言数据清洗实战——世界濒危遗产地数据爬取案例
- Leetcode-Easy 437. Path Sum III
- R语言爬虫实战——网易云课堂数据分析课程板块数据爬取
- 左手用R右手Python系列14——日期与时间处理
- 如何使用管道操作符优雅的书写R语言代码
- 第四周编程作业(二)-Deep Neural Network for Image Classification: ApplicationDeep Neural Network for Image Cl
- 第四周编程作业(一)-Building your Deep Neural Network: Step by StepBuilding your Deep Neural Network: Step by
- Python数据抓取与可视化实战——网易云课堂人工智能与大数据板块课程实战
- 商务图表案例——仿经济学人分组漏斗图~
- 第二周编程作业 -Logistic Regression with a Neural Network mindsetLogistic Regression with a Neural Network
- 左手用R右手Python系列——任务进度管理
- JavaScript 教程
- JavaScript 编辑工具
- JavaScript 与HTML
- JavaScript 与Java
- JavaScript 数据结构
- JavaScript 基本数据类型
- JavaScript 特殊数据类型
- JavaScript 运算符
- JavaScript typeof 运算符
- JavaScript 表达式
- JavaScript 类型转换
- JavaScript 基本语法
- JavaScript 注释
- Javascript 基本处理流程
- Javascript 选择结构
- Javascript if 语句
- Javascript if 语句的嵌套
- Javascript switch 语句
- Javascript 循环结构
- Javascript 循环结构实例
- Javascript 跳转语句
- Javascript 控制语句总结
- Javascript 函数介绍
- Javascript 函数的定义
- Javascript 函数调用
- Javascript 几种特殊的函数
- JavaScript 内置函数简介
- Javascript eval() 函数
- Javascript isFinite() 函数
- Javascript isNaN() 函数
- parseInt() 与 parseFloat()
- escape() 与 unescape()
- Javascript 字符串介绍
- Javascript length属性
- javascript 字符串函数
- Javascript 日期对象简介
- Javascript 日期对象用途
- Date 对象属性和方法
- Javascript 数组是什么
- Javascript 创建数组
- Javascript 数组赋值与取值
- Javascript 数组属性和方法