第五十二天| 300.最长递增子序列、674. 最长连续递增序列、718. 最长重复子数组

Leetcode 300.最长递增子序列

题目链接:300 最长递增子序列

题干:给你一个整数数组 nums ,找到其中最长严格递增子序列的长度。

子序列 是由数组派生而来的序列,删除(或不删除)数组中的元素而不改变其余元素的顺序。例如,[3,6,2,7] 是数组 [0,3,1,6,2,2,7] 的子序列。

思考:动态规划。难点:如何将问题看成连续重复子问题。本题给定数组长度为处理区间,如果固定数组首个元素作为子处理区间头部,从第二个元素依次向后移动作为子处理区间尾部以及递增子序列的最大值,统计每个递增子序列的长度并比较,其中最大值便是题目要求的。


  • 确定dp数组以及下标的含义

dp[i]表示i之前包括i的以nums[i]结尾的最长递增子序列的长度

为什么一定表示 “以nums[i]结尾的最长递增子序” ,因为做 递增比较的时候,如果比较 nums[j] 和 nums[i] 的大小,那么两个递增子序列一定分别以nums[j]为结尾 和 nums[i]为结尾, 要不然这个比较就没有意义了,不是尾部元素的比较那么 如何算递增呢。

  • 确定递推公式

位置i的最长升序子序列等于j从0到i-1各个位置的最长升序子序列 + 1 的最大值。

所以:if (nums[i] > nums[j]) dp[i] = max(dp[i], dp[j] + 1);

  • dp数组如何初始化

每一个i,对应的dp[i](即最长递增子序列)起始大小至少都是1(即nums[i]这一个元素)。

  • 确定遍历顺序

dp[i] 是有0到i-1各个位置的最长递增子序列 推导而来,那么遍历i一定是从前向后遍历。

而内层循环 遍历数组其实就是遍历0到i-1,那么是从前到后,还是从后到前遍历都无所谓,只要将 0 到 i-1 的元素都遍历一次即可。 (下面代码采取从前向后遍历)

遍历i的循环在外层,遍历j则在内层,代码如下:

  • 举例推导dp数组

举例:[0,1,0,3,2],dp数组的变化如下:

代码:

class Solution {
public:int lengthOfLIS(vector<int>& nums) {vector<int> dp(nums.size(), 1);     //dp[i]:以nums[i]结尾的最长严格递增子序列长度int result = 1;     //记录最大长度for (int i = 1; i < dp.size(); i++) {       //遍历子序列区间for (int j = 0; j < i; j++) {           //遍历整数数组if (nums[j] < nums[i])      //保持严格递增dp[i] = max(dp[i], dp[j] + 1);}result = max(result, dp[i]);}return result;}
};

Leetcode 674. 最长连续递增序列

题目链接:674 最长连续递增序列

题干:给定一个未经排序的整数数组,找到最长且 连续递增的子序列,并返回该序列的长度。

连续递增的子序列 可以由两个下标 l 和 rl < r)确定,如果对于每个 l <= i < r,都有 nums[i] < nums[i + 1] ,那么子序列 [nums[l], nums[l + 1], ..., nums[r - 1], nums[r]] 就是连续递增子序列。

思考一:动态规划。

  • 确定dp数组(dp table)以及下标的含义

dp[i]:以下标i为结尾的连续递增的子序列长度。

  • 确定递推公式

如果 nums[i] > nums[i - 1],那么以 i 为结尾的连续递增的子序列长度 一定等于 以i - 1为结尾的连续递增的子序列长度 + 1 。即:dp[i] = dp[i - 1] + 1;

因为本题要求连续递增子序列,所以就只要比较nums[i]与nums[i - 1],而不用去比较nums[j]与nums[i] (j是在0到i之间遍历)。

因此也不用两层for循环,本题一层for循环就行,比较nums[i] 和 nums[i - 1]。

  • dp数组如何初始化

以下标i为结尾的连续递增的子序列长度最少也应该是1即nums[i]这一个元素。所以dp[i]应该初始1

  • 确定遍历顺序

从递推公式上可以看出, dp[i + 1]依赖dp[i],所以一定是从前向后遍历。

  • 举例推导dp数组

举例:nums = [1,3,5,4,7],dp数组状态如下:

代码:

class Solution {
public:int findLengthOfLCIS(vector<int>& nums) {vector<int> dp(nums.size(), 1);     //dp[i]:以nums[i]结尾的最长最长连续递增子序列长度int result = 1;     //记录最大长度for (int i = 1; i < nums.size(); i++) {if (nums[i] > nums[i - 1])      dp[i] = dp[i - 1] + 1;      //连续递增则长度加一if (result < dp[i])     result = dp[i];     //更新最大长度}return result;}
};

思考二:贪心法。只要遇到nums[i] > nums[i - 1]的情况,count就++,否则count为1,记录count的最大值就行。

代码:

class Solution {
public:int findLengthOfLCIS(vector<int>& nums) {int result = 1;     //记录最大长度int count = 1;      //记录当前子序列长度for (int i = 1; i < nums.size(); i++) {     //遍历数组if (nums[i] > nums[i - 1])count++;        //连续递增则长度加一elsecount = 1;      //不连续递增则重置长度if (result < count)     result = count;     //更新最大长度}return result;}
};

Leetcode 718. 最长重复子数组

题目链接:718 最长重复子数组

题干:给两个整数数组 nums1 和 nums2 ,返回 两个数组中 公共的 、长度最长的子数组的长度 

  • 1 <= nums1.length, nums2.length <= 1000
  • 0 <= nums1[i], nums2[i] <= 100

思考:动态规划。此题如果暴力解,两个for循环内部再加个while循环,时间复杂度大。可以选用空间换时间,用二维数组可以记录两个字符串的所有比较情况。

  • 确定dp数组(dp table)以及下标的含义

dp[i][j] :以下标为nums1[i - 1]和nums2[j - 1]结尾的最长公共子数组长度

从定义可以看出,在遍历dp[i][j]的时候i 和 j都要从1开始。

为什么将dp[i][j] 定义为 以下标为nums1[i]和nums2[j]结尾的最长公共子数组长度,下面初始化会解释。

  • 确定递推公式

从dp[i][j]的定义可以看出,dp[i][j]的状态只能由dp[i - 1][j - 1]推导出来。

即当nums1[i - 1] 和nums2[j - 1]相等的时候,dp[i][j] = dp[i - 1][j - 1] + 1;

由递推公式可以看出,遍历dp[i][j]的时候i 和 j都要从1开始。

  • dp数组如何初始化

从dp[i][j]的定义可以看出,dp[i][0] 和dp[0][j]其实都是没有意义的。

那为什么上面这么定义dp数组?

从递推公式来看如果 将dp[i][j] 定义为 以下标为nums1[i]和nums2[j]结尾的最长公共子数组长度 那么初始化操作要先将dp数组第一行和第一列优先处理,再进行循环处理后面的dp数组。代码不简洁。

由递推公式可以看出,dp数组的每个元素都可初始化为0。

  • 确定遍历顺序

外层for循环遍历nums1,内层for循环遍历nums2 或 外层for循环遍历nums2,内层for循环遍历nums1都行。

同时题目要求长度最长的子数组的长度。所以在遍历的时候顺便把dp[i][j]的最大值记录下来。

  • 举例推导dp数组

举例:nums1: [1,2,3,2,1],nums2: [3,2,1,4,7],dp数组的状态变化如下:

代码:

class Solution {
public:int findLength(vector<int>& nums1, vector<int>& nums2) {//dp[i][j]:以下标为nums1[i - 1]和nums2[j - 1]结尾的最长公共子数组长度vector<vector<int>> dp(nums1.size() + 1, vector<int>(nums2.size() + 1, 0));int result = 0;     //记录公共子数组最大长度for (int i = 1; i <= nums1.size(); i++) {           //遍历数组1for (int j = 1; j <= nums2.size(); j++) {       //遍历数组2if (nums1[i - 1] == nums2[j - 1])dp[i][j] = dp[i - 1][j - 1] + 1;        //连续相同则加一if (dp[i][j] > result)result = dp[i][j];      //更新最大值}}return result;}
};

自我总结:

动态规划dp数组的定义要考虑到各种情况来定义,以及将处理区间逐步增大的思路。

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

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

打造一款用于照片局部修复的“在线橡皮擦”应用(基于Django5和Pytorch,含完整代码)

目录 一、任务概述二、Django微服务开发2.1 创建项目2.1.1 创建Django项目2.1.2 创建主页面2.1.3 编写视图处理函数2.1.4 配置访问路由url2.1.5 启动项目 2.2 前端开发2.2.1 集成Bootstrap52.2.2 初始化各组件2.2.3 自适应展示图像2.2.4 橡皮擦涂抹2.2.5 使用Ajax传输图像 2.3 …

新代超行程报警,如何解除

新来的操作员&#xff0c;在没有回原点之前&#xff0c;手动按出了行程&#xff0c;可以通过解除按扭来解除。 具体操作如下&#xff1a; 1、打到手轮模式 2、边按着【超行程解除】按扭&#xff0c;边反向摇手轮&#xff0c;即可解除报警。

graylog API 弱密码

graylog web 页面密码设置 输入密码&#xff1a;获取sha256加密后密码 echo -n "Enter Password: " && head -1 </dev/stdin | tr -d \n | sha256sum | cut -d" " -f1vi /etc/graylog/server/server.conf #修改以下配置 root_usernameroot ro…

SAP MD04界面中MRP元素翻译

通常在运行完MRP后,PMC就会去看MD04界面中的供需平衡的情况,通常我们看到的MRP元素都是显示英文的状态 ,如下图 可以看到在MRP元素中显示的是英文的状态,一旦需求多了以后PMC看起来就很费劲,就会要求把MRP元素翻译成中文。 SAP有一个后台的配置点:Tcode:OMD5 如下图 …

【leetcode热题】环形链表 II

难度&#xff1a; 中等通过率&#xff1a; 30.1%题目链接&#xff1a;. - 力扣&#xff08;LeetCode&#xff09; 题目描述 给定一个链表&#xff0c;返回链表开始入环的第一个节点。 如果链表无环&#xff0c;则返回 null。 为了表示给定链表中的环&#xff0c;我们使用整数…

Uniapp + SpringBoot 开发微信H5项目 微信公众号授权登录 JAVA后台(一、配置使用微信公众平台测试公众号)

申请测试号进行调试开发&#xff0c;测试号拥有大部分服务号有的接口权限。 一、接口配置信息填写校验 这里需要填写一个URL和一个Token验证字符串 我这里是用了natapp内网穿透 将本地的后台8080端口服务映射到了 http://x7zws8.natappfree.cc https://natapp.cn/在natapp官网…

GEE 底图加载——自定义底图样式加载案例分析(含免费引如多款底图)

在本教程中&#xff0c;您将学习如何更改地图对象的选项&#xff0c;以便为底层基础地图定义自己的样式。 地球引擎中的默认地图 地球引擎的基础地图是 Google Map API 中的地图。默认选项包括 roadmap&#xff0c;显示默认的路线图视图、卫星&#xff0c;显示谷歌地球卫星图…

Leetcode : 面试题 10.01. 合并排序的数组

思路&#xff1a;设定两个指针ptrA和ptrB&#xff0c;遍历两个数组比较&#xff0c;对A数组进行修改&#xff1b; A.insert添加&#xff0c;最后进行A.erase删除多余元素&#xff0c;提醒&#xff0c;数组长度提前记录一下&#xff0c;方便后续删除 #include <iostream>…

数据可视化原理-腾讯-分类散点图

在做数据分析类的产品功能设计时&#xff0c;经常用到可视化方式&#xff0c;挖掘数据价值&#xff0c;表达数据的内在规律与特征展示给客户。 可是作为一个产品经理&#xff0c;&#xff08;1&#xff09;如果不能够掌握各类可视化图形的含义&#xff0c;就不知道哪类数据该用…

付强:基于注意力机制的听觉前端处理 | 嘉宾公布

一、智能家居与会议系统专题论坛 智能家居与会议系统专题论坛将于3月28日同期举办&#xff01; 智能会议系统它通过先进的技术手段&#xff0c;提高了会议效率&#xff0c;降低了沟通成本&#xff0c;提升了参会者的会议体验。对于现代企业、政府机构和学术界是不可或缺的。在这…

GitHub登不上:修改hosts文件来解决(GitHub520,window)

参考链接&#xff1a;GitHub520: 本项目无需安装任何程序&#xff0c;通过修改本地 hosts 文件&#xff0c;试图解决&#xff1a; GitHub 访问速度慢的问题 GitHub 项目中的图片显示不出的问题 花 5 分钟时间&#xff0c;让你"爱"上 GitHub。 (gitee.com) GitHub网站…

阿里云服务器怎么使用?3分钟搭建网站教程2024新版

使用阿里云服务器快速搭建网站教程&#xff0c;先为云服务器安装宝塔面板&#xff0c;然后在宝塔面板上新建站点&#xff0c;阿里云服务器网aliyunfuwuqi.com以搭建WordPress网站博客为例&#xff0c;来详细说下从阿里云服务器CPU内存配置选择、Web环境、域名解析到网站上线全流…