自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(42)
  • 收藏
  • 关注

原创 代码随想录第四十二天|买卖股票的最佳时机 III|买卖股票的最佳时机 IV

初始化:dp[0][0]=0,dp[0][1]=0;本题就分为五种情况,dp[i][0]表示在第i天不持有股票状态的最大利润为dp[i][0],dp[i][1]表示在第i天第1次不持有股票状态的最大利润为dp[i][1].dp[i][3]表示在第i天第2次不持有股票状态的最大利润为dp[i][3].dp[i][2]表示在第i天第1次持有股票状态的最大利润为dp[i][2].dp[i][4]表示在第i天第2次持有股票状态的最大利润为dp[i][4].递推公式:dp[i][0]=dp[i-1][0];

2024-05-13 19:34:45 143

原创 代码随想录第四十一天|买卖股票的最佳时机|买卖股票的最佳时机II

这一题与上一题的区别就在于,不只是只能买卖一次,可以买卖多次,在贪心中,可以将所有的正利润收集起来,就是最大利润。这里使用动态规划的方法。dp数组含义以及初始化和遍历顺序都和上一题一致。在递推公式上有点区别。

2024-05-11 15:08:38 307

原创 代码随想录第四十天|打家劫舍 |打家劫舍II |打家劫舍III

这是将数组改成了二叉树,这是树形dp的入门题。既然是二叉树,就要考虑使用什么遍历方式,递归和递归三部曲。这里必须使用后序遍历,因为要先将两个孩子上的最大钱数算出来,然后去当前节点偷还是不偷进行比较,如果不偷当前节点,那就偷孩子节点。这里数组变成了环形的,首位相连。头节点和尾结点不能同时取。那就进行分类,分成只取头结点时所能偷的最大钱数和只取尾结点时所能偷的最大钱数。这个就和爬楼梯很像,只不过这个每次只能走两步,求最后偷到钱的最大价值。

2024-05-10 23:11:10 411

原创 代码随想录第三十九天|单词拆分|背包问题总结

单词字典就是物品,字符串就是背包,看字典里的单词能不能拼接出字符串,就是用单词能不能装满字符串长度的背包。完全背包,每种物品能使用多次,那就接触倒序遍历的限制,然后遍历顺序也能够颠倒。但是在特定的问题中遍历顺序也是有讲究的。,顺序不能颠倒,因为需要倒序遍历,如果颠倒的话会导致每个背包中只有一件物品。,每种物品只能使用一次,在遍历背包的时候,需要。

2024-05-08 22:15:07 399

原创 代码随想录第三十八天(完全背包问题)|爬楼梯(第八期模拟笔试)|零钱兑换|完全平方数

这一题也是求放入背包中的物品数,但是不是就放满指定容量背包的最大物品数,而是最小物品数。求最少物品数和最大物品数的区别在于两个地方,一个是递推公式,还有就是初始化,因为要求最小物品数,所以除了dp[0]以外,所有的元素都需要初始化成int的最大值,才能保证在递推公式计算中被覆盖。这一题和上面一题解法一样,只是要先将完全平方数求出。该题也是昨天的完全背包排列问题,解法相同,将遍历顺序进行调换。

2024-05-07 14:47:43 291

原创 代码随想录第三十七天(完全背包问题)|完全背包|零钱兑换 II|组合总和 Ⅳ

在完全背包中,在求装满指定容量背包的组合总数的时候,遍历顺序非常重要,只求组合总数的话,先遍历物品,后遍历背包,因为先遍历物品的话,每次都会将前一个物品先添加进去,只会出现{1,2}这样的组合,不会出现{2,1}的组合。当背包容量为3,假如已取物品1,也就是先放入重量为2的物品,剩余只能取重量为1的组合了,就出现了{2,1},而假如已取的是物品0,也就是先放入重量为1的物品,剩余只能取重量为2的组合,因为在上一个状态遍历了物品1,已经有了重量2的组合,就出现了{1,2}和{1,1,1}的组合了。

2024-05-06 21:08:38 266

原创 代码随想录第三十六天(背包问题)|最后一块石头的重量 II |目标和|一和零

动规应用题,主要是怎么将这道题分析出来使用动规方法来做,要完全理解题目,才能想到这个方法,将石头分为尽可能重量相等的两堆,设每一堆重量为target,看看给定容量为target的背包,尽可能能装多少,最后剩下的就是最后一块石头的重量了。已经有一个1(nums[i]) 的话,有 dp[4]种方法 凑成 容量为5的背包。只要搞到nums[i],凑成dp[j]就有dp[j - nums[i]] 种方法。最后一块石头的重量 II ,讲的是容量为j的背包,尽可能的装,能装多少是多少,有点像经典01背包的最大价值。

2024-05-06 11:30:30 524

原创 代码随想录第三十五天(背包问题)| 二维数组|滚动数组

从递推公式可以看出,当前层容量为j的背包所能装的最大价值为dp[j],所以dp[j]的最大值,就是放入当前物品i和不放入当前物品i的最大值。在在二维dp数组中,dp[i][j]的状态都和dp[i-1]有关,这里为了节省空间,可以把二维dp数组压缩成一维dp数组,因为总是依赖于二维矩阵中上侧和上左侧的状态,所以直接将上侧的状态拷贝到当前层来,每次遍历一个物品,就把所有的值拷贝到当前物品层来,看着就像是数组在滚动更新一样,所以也叫滚动数组,这里的拷贝操作是怎么实现的呢?初始化:dp[j]初始化全为0。

2024-05-05 10:42:52 641

原创 代码随想录第三十四天(动态规划)| 整数拆分|不同的二叉搜索树

五部曲,拆分整数,给定一个整数n,第一个数从1开始拆,会剩下n-1,于是从这里可看出,n-1又可以继续分为1和n-1.现有的状态依赖之前的状态,于是可以看出dp数组的定义了。计算完1之后,递增从2又开始拆。这一题可以看出,选择不同的头结点,其左右子数就是之前经历过的状态。这里没有想到是dp[左子树]*dp[右子树]。只发现了当前状态可以拆分成之前的状态。

2024-04-29 20:35:59 158

原创 代码随想录第三十三天(动态规划)| 不同路径| 不同路径 II

第一题递归五部曲和上一题一致,只是有两个注意的点。在一个m*n的网格中找到达某一位置的路径数量。

2024-04-28 21:11:57 217

原创 代码随想录第三十二天(动态规划)| 斐波那契数| 爬楼梯| 使用最小花费爬楼梯

这题要明确考虑的是方法数量,而不是步数。以三阶为例,先迈1阶再迈2阶,我的错误想法是,先走1阶有几种方法,然后加上走2阶有几种方法。这里就是算的有多少种步数方法了。而正确的想法应该是,后面的迈2阶已经确定了,就只有这一种方式,剩下的就是看前面的迈1阶有几种方式。同理,假如此时在2阶上,只需要迈1阶就能到达,此时就是看到2阶的有几种方法。两种方法相加就是最后的方法数。这题是上一题的拓展。

2024-04-27 15:18:10 124

原创 代码随想录第三十一天|单调递增的数字| 监控二叉树

然后这里是设置一个标志位来记录要置9的区间。因为如果不符合规则才置9的话,遇到1000这种特殊情况结果就是900,不符合条件,所以需要一个标志位来记录一个区间。这里是数字,怎么比较好的对其各个位进行处理呢?这里是通过将数字转为字符串,然后将字符串转为字符数组来进行遍历比较。最后将字符数组转为字符串再转为数字返回。保证数字单调递增,就需要保证从个位数起依次递减,若十位和个位不符合递减规则,则十位将减一,个位将置为9.大致思路就是如此。但是有几个细节还需注意。此题困难,二刷再解决。

2024-04-25 20:14:47 225

原创 代码随想录第三十天|无重叠区间| 划分字母区间| 合并区间

这一题和昨天的最少多少支箭射爆气球的解法是相同的,判断相邻区间是否重叠,若两个区间重叠了则找出重叠区间最小右边界,更新区间去和下一个区间做判断。那么怎么求最远下标呢?这里需要想到哈希数组,因为这里都是字母,元素有限,可以将每个字母元素的下标映射到哈希数组中,因为每个位置都只对应着一个元素,遇到相同字母时就会刷新哈希数组中的下标元素,找到每个字母所对应的最远下标。合并区间和第一题也类似,只是合并区间的时候要找重叠区间的最大右边界,然后更新当前区间,删除结果集中的上一个末尾元素,再将更新后的加入到结果集中。

2024-04-24 20:33:53 324

原创 代码随想录第二十九天|柠檬水找零| 根据身高重建队列| 用最少数量的箭引爆气球

这是一道重叠区间的题,首先将数组进行升序排序,判断两个相邻数组是否相交,若是相交,就只需要一支箭就能射爆两个气球,当相邻三个数组都相交的时候,也是同理,但是怎么判断三个数组相交呢?就是当两个数组相交时,将重叠区域的最小右边界作为第二个数组的右边界,来继续和它的下一个数组的左边界进行比较,若是相交,那就是三个数组相交,同理n个数组也是。这一题和之前的分发糖果很像,有两个维度,一个是身高维度k,一个是前面有比其高的人数k,对于有两个维度的题,先解决一个维度之后再去解决另外一个维度,不要两个维度同时去解决。

2024-04-23 22:23:25 260

原创 代码随想录第二十八天| K 次取反后最大化的数组和 | 加油站| 分发糖果

首先要计算每个站点加油量和耗油量之间的差值,也就是每个站点净增的油量,使用cursum来记录站点的净增油量之和,若某一个点净增油量之和小于0时,则这个点以及这个点之前的点都不能作为出发点,因为都没有油了,到不了下一个点了,所以这里选择这个点的下一个点作为起点,同时还计算所有站点的净增油量总和,要是大于0,则一定能循环一圈,因为从起点开始到cursum<0的点所净增的油能支撑这一站点的消耗。首先评分高的孩子能比相邻的孩子拿的糖果多,这里就有两种情况,一种是他与左边孩子比较,一种是与右边孩子比较。

2024-04-22 21:57:53 181

原创 代码随想录第二十七天| 买卖股票的最佳时机 II | 跳跃游戏| 跳跃游戏 II

就是当遍历到当前覆盖范围的最后位置时,往后跳一步刷新范围,但是跳到什么位置能保证刷新的是最大覆盖范围呢?这里引入一个覆盖范围的概念,每个位置的最大步数就叫这一步的覆盖范围,在这个覆盖范围上的位置都能跳上去。所以每个位置都跳最大步数,不断更新最大覆盖范围,当最大覆盖范围大于或者等于目标位置时,就是true。这里有个巧妙的方法,其实某天到某天的利润最大,就是在这几天里哪几天利润都是正数,然后把这几天利润加起来就是最大的利润了,所以只要把每天的利润计算出来,把正利润相加,就是最大利润了。

2024-04-20 21:21:17 286

原创 代码随想录第二十六天(贪心算法)| 分发饼干 | 摆动序列| 最大子数组和

这题要解决三种情况,一种是首尾的情况,因为它们只有两个元素,要判断摆动点的话需要三个点。这一题最重要的就是要明确在连续子数组和为负数的时候,就跳过之前的元素,选择下一个元素作为子数组的起点,这个操作是通过给子数组和count置零实现的,相当于从下一个元素开始重新计算和。这一题为了不浪费饼干,每个孩子只能拿一块饼干,不能将大的饼干去喂小胃口的孩子,那样就浪费了,到时候小的饼干又喂不了大胃口的小孩,所以先用大饼干喂大胃口的孩子,满足大胃口的孩子之后,再去喂小胃口的孩子。

2024-04-20 11:09:25 173

原创 代码随想录第二十五天| 回溯算法总结

中又能分为两种组合问题,一种是在一个集合中找出所以符合条件的组合,另一种是在多个集合中找出符合条件的组合。不过模版是同样的,只是细节更多一些。排列问题和组合问题区别就在于,排列是讲究顺序的,不同的顺序也是符合条件的,同样使用模版,只是组合问题中的startindex在排列中就失效,需要使用一个used数组来标记已经加入过path数组中的元素,防止重复加入。其实子集问题也可以归在组合问题里面,同时切割问题实际上也是组合问题,只有一些参数比如startindex有新的含义,就是代表切割线。

2024-04-18 21:42:47 199

原创 代码随想录第二十四天| 非递减子序列 | 全排列| 全排列 II

于是,之前在组合问题中使用的startindex在排列中就失效了,排列不需要排除在同一个树层中之前使用过的元素。在代码中,每一层递归都new一个新的set,用来保证当前层不使用重复元素进行组合。这里使用used数组来进行标记,每取一个元素,在相应的used数组位置置1,证明该元素已取过。排列和组合最大的区别就是组合不讲究顺序,只要数组中元素相同即是一个组合,而排列即使是数组中元素相同 ,只要元素的顺序不同,就是一种新的排列。去重的两种方法:1.数组可以排序的情况下,同样使用used数组标记来进行去重。

2024-04-17 21:42:54 173

原创 代码随想录第二十三天| 复原IP地址 |子集| 子集 II

解决分割字符串和加逗点的问题:在之前的二叉树章节,收集路径总和是用stringbuilder收集路径值,在终止条件中遍历stringbuilder在其中加上箭头。而在本题中,直接在单层逻辑处理中对字符串作处理,在符合条件的分割出来的子串后面加上逗点构成新的字符串。终止条件的判断逻辑也是使用了逗点,这里用逗点数作为终止条件,当存在三个逗点后,且最后的子串也符合条件的话,则将整个加了逗点的新字符串放入结果集中,若是不符合条件,则进行回溯,同时删除之前添加的逗点,重新分割子串。使用回溯模版方法加上标识数组。

2024-04-16 20:13:35 117

原创 代码随想录第二十二天| 组合总和 |组合总和 II|分割回文串

这里分割字符串实际上操作和数组的组合问题很像,只是这里的startindex多了一层含义,上面数组的组合问题中startindex表示子数组递归的起点,而在这里startindex表示字符串分割的位置。去重的方法:首先将数组排序,于是相同的数字会在一起,使用一个标识数组来标识相同数字的使用情况,若是当前数字和上一个数字相同,则当前数字后面的所有数字都被上一个数字组合过,若是有符合条件的情况,就已经被加入结果集中了,所以需要跳过当前数字。

2024-04-15 20:44:30 177

原创 代码随想录第二十一天| 组合总和 III |电话号码的字母组合

该题和上面的组合问题有些区别,组合问题是在一个集合中选出元素组合成不同的元素集合。而本题是在多个集合中选出元素组合成不同的元素组合。所以上一题中的startindex在本题中就不适用,因为startindex是用来表示集合中下一个子问题递归的起点是什么,防止重复使用同一个元素。这里是多个集合中的元素组合,所以起点直接从零开始。然后本题还有一个就是数子到字符串的映射,解决办法是使用字符相减。使用stringBuilder来存放路径。此题和昨天的组合题类似,使用回溯模版方法。

2024-04-13 21:41:47 163

原创 代码随想录第二十天|回溯算法理论基础 |组合

每一个集合操作对应着一个for循环,for循环里面嵌套着递归,递归是处理子集合。for循环式横向遍历,递归是纵向遍历,解决子问题。这是回溯算法的经典题。每一个节点对应着一个for循环,在递归函数后加上回溯,就相当于从子集那一层返回到上一层节点。回溯法可以抽象为树形结构,回溯法解决的都是在集合中查找子集,集合的大小就是树的宽度,递归的深度就构成了树的深度。回溯算法是一种暴力搜索算法,采用递归+回溯搜索。

2024-04-12 20:47:36 120

原创 代码随想录第十九天|修剪二叉搜索树 |将有序数组转换为二叉搜索树|把二叉搜索树转换为累加树

单层处理逻辑:在遇到要删除的节点时,不能立马删除,要判断其左子树或者右子树中是否还有符合条件的子树,于是递归其左子树或者右子树,当成更小的问题来解决。然后这里删除一个节点的操作,是将该节点的父节点指向符合条件的子树根节点,返回了两层递归,就能实现这个效果。这一题和以前的构造二叉树解法一致,找到数组中心的位置作为根节点,然后根据这个节点将数组分为左右子区间,重复这个操作过程,将每一层找到的根节点返回到上一层递归中作为上一层递归节点的左节点或者右节点。终止条件:遍历到叶子节点。

2024-04-11 22:11:20 206

原创 代码随想录第十八天|二叉搜索树的最近公共祖先 |二叉搜索树中的插入操作|删除二叉搜索树中的节点

递归新的理解:对于二叉树的各项遍历,中是处理的节点,左右是递归遍历,当前层中处理完之后的结果是返回给上一层递归的变量,上一层递归可以是左子树递归或者是右子树递归,这里只需要在左子树递归和右子树递归的后面写对应的后续方法即可,不用讨论该返回到左子树递归还是右子树递归。因为二叉搜索树中序遍历递增的特性,中间节点的值介于左右子树的值之间,假如p在根节点的左子树中,q在根节点的右子树中,如果节点向左或者向右遍历的话,就一定会错过其中一个了。:当节点值大于q和p时,向左遍历,当节点值小于p和q时,向右遍历。

2024-04-10 21:26:19 297 1

原创 代码随想录第十七天|二叉搜索树的最小绝对差 |二叉搜索树中的众数 |二叉树的最近公共祖先

定义一个count和maxcount,当pre指针和cur指针指向的元素值相等时,count自增,然后将count与maxcount进行比较,若是count等于maxcount,则将元素值存起来,若count大于maxcount,则将数组清空,重新存下这个出现频次最高的新数值,因为这是二叉搜索树,中序遍历,所以元素都是递增的,相同元素都是连续出现。另一种是没有众数,要把所有的出现过一次的节点值全部返回,这里就有一个代码的技巧,也是我代码写太少,积累不行;:若找到p和q后返回到同一节点,则直接返回节点;

2024-04-09 22:51:09 306 1

原创 代码随想录第十六天|最大二叉树 |合并二叉树 |二叉搜索树中的搜索 |验证二叉搜索树

先左子树递归找到最左边的叶子节点,定义一个“指针”执行最左边的叶子节点,每一次递归返回的时候,指针也跟着递归移动接着指向返回的节点。利用二叉搜索树的特性,递归和迭代法都好实现,这里遇到了一个小问题,就是如果全是返回值全在if语句中的话,编译器会报错,没有返回值,因为编译器会认为加入全都不满足if判断条件的话就回没有返回值。如果tree1为null,则直接合并tree2,同理,tree2为null时,直接合并tree1.这里很巧妙,将tree1和tree2同时为null的情况也进行了合并。

2024-04-08 21:49:51 311

原创 代码随想录第十五天|找树左下角的值 |路径总和 |从中序与后序遍历序列构造二叉树

只不过这里有个需要注意的点,就是将一维数组存入二维数组中时,不能直接存,因为直接存,存的相当于是一维数组的指针,一维数组在后续回溯发生变化时,二维数组也会变化,导致错误。该题和昨天的求二叉树所有路径的题解法基本一致,采用前序遍历,将中间节点先加入路径数组中,再遍历左子树和右子树,当遍历到叶子节点后,将路径之后存到结果数组中。:遍历到叶子节点,将当前深度赋值给深度变量,同时将叶子节点的值赋给结果变量,当遍历完所有叶子节点后,将取得最大深度的叶子节点的值,将结果变量返回即可。:遍历到叶子节点,保存路径之和。

2024-04-06 22:57:57 226 1

原创 代码随想录第十四天|平衡二叉树|二叉树的所有路径|左叶子之和

判断平衡二叉树,即判断中间节点的左子树和右子树的高度之差不大于1.使用后序遍历,将左右子树的高度收集起来,相减进行判断。:遍历左子树,当遇到叶子节点之后会返回到中间节点,此时通过中间节点(父节点)判断该叶子节点是否为左叶子节点,若是左叶子节点,收集其值。在终止条件之前,因为遍历到叶子节点时,需要将路径添加进结果集中进行返回,如果将中间节点处理放在终止条件之后,将会遗漏最后的叶子节点。为遍历左子树方向,遍历完左子树中的路径后进行回溯,继续向右子树方向遍历,遍历完右子树中的路径后进行回溯。

2024-04-05 21:44:19 257 1

原创 代码随想录第十三天|二叉树的最大深度|二叉树的最小深度|完全二叉树的节点个数

这里还有最主要的是选择遍历的方法。因为是找最大深度,可以将左子树和右子树的深度返回给中间节点,适合使用后序遍历。然后对于中间节点的处理逻辑,将左子树和右子树中深度最大的加上1后(这里加一是因为中间节点也占一个位置,算一个深度)进行返回。递归法:这里求最小深度和最大深度有一些区别,这里的最小深度是离根节点最近的叶子节点的深度。今天的三道题分别使用层序遍历的模版方法和递归法进行解决。递归法:这里使用后序遍历,直接统计左子树和右子树的节点数,返回给根节点然后加上根节点本身即可统计出节点数。

2024-04-04 20:43:01 154 1

原创 代码随想录第十二天|二叉树的层序遍历|翻转二叉树|判断对称二叉树

处理二叉树相关问题时,先要考虑使用什么遍历方法,因为中间节点的位置不一样,处理问题的复杂程度也不一样。前序遍历和后序遍历,能够比较轻松解决,因为前序遍历和后序遍历,中间节点的操作在左右的前面和后面,不影响递归中左子树的左右孩子的交换。这里对称二叉树只能选择后序遍历,因为这里递归,需要对叶子节点进行比较,将比较的结果传回中间节点,通过递归操作,最终返回到root节点。需要比较外侧的节点和内侧的节点是否对应相等。二叉树的层序遍历使用队列进行操作,因为队列先入先出的特性符合层序遍历的逻辑。

2024-04-04 00:30:29 283 1

原创 代码随想录第十一天|二叉树的前中后序遍历|递归解法 |迭代解法

首先遍历的节点和要处理的节点是一致的,要处理的节点是中间节点,也就是最开始的根节点。所以首先加入根节点,在遍历的时候,一开始就可以将要处理的节点加入数组中,然而栈是先入后出的,中左右的入栈顺序需要调换成中右左,出栈的时候就是中左右了,中间节点不需要做处理,因为一开始就将中间节点弹出保存了。中序遍历因为一开始遍历的节点和要处理的节点不同,所以不能用上面的方法,这里需要先找到要处理的节点,也就是没有左孩子的中间节点,加入数组后判断右孩子是否存在,若不存在,则直接弹出栈中元素,和递归有点类似。

2024-04-02 21:46:15 126 1

原创 代码随想录第十天|滑动窗口最大值|前 K 个高频元素

这一题只需要取前k个高频元素即可,非常适合用大小顶堆优先队列来解决,但是这里最好使用小顶堆,因为使用大顶堆,每次弹出的元素是根节点,是出现频次最大的元素。上述代码中((pair1,pair2)->pair1[1]-pair2[1])用来设置优先队列是大顶堆还是小顶堆,这里使用pair1[1]-pair2[1]两个元素相减,若结果为负数,则将第一个元素pair1放在前面,若为正数,则将第二个元素pair2放在前面,返回零时,两个元素顺序不变。通过第二题,熟悉了map的方法操作和优先队列的方法操作。

2024-04-01 22:09:14 316

原创 代码随想录第九天|有效的括号|删除字符串中的所有相邻重复项 |逆波兰表达式求值

这里有一种巧妙的办法,从左到右,遇到左括号时往栈中压入右括号,当遇到右括号时,弹出栈顶元素与其匹配,若是不匹配,则是属于情况二;这里还有一种技巧,就是在遇到右括号时,正面需要判断是哪一种右括号,而且要判断是否匹配,写起来十分麻烦,这里先写出不符合条件不匹配的右括号的情况,剩下直接一个else即可包含所有需要讨论的正面匹配的情况。今天是栈的应用练习,通过这几题可以发现,栈非常适合“消消乐”类型的问题,消除相邻相同元素,因为栈能够记录当前元素的同时还能记录当前元素的上一个元素。

2024-03-30 21:39:42 138 1

原创 代码随想录第八天|栈模拟队列|队列模拟栈 |外加拓展,k个一组反转链表

这里利用之前反转链表的方法,但是要分段,每一段的头结点最后是要指向第二段的头结点。这里直接设计一个反转函数,传入指针cur和k作为参数,反转cur后的k个节点。使用root节点指向cur,在对root节点后的k个节点进行反转时,要使用cur进行遍历,判断root节点后是否还有k个节点。这里直接引用大神的图。java中推荐使用Deque(双端队列)来代替stack。这里给出初始化一个Deque的方法以及对应栈和单端队列的方法。使用两个栈实现队列功能,代码较为简单。重点要熟悉Deque的方法。

2024-03-29 20:42:57 111 1

原创 代码随想录第七天|反转字符串|反转字符串II |.替换数字|翻转字符串里的单词|右旋转字符串

这题使用了java中character类中的isdigit方法进行数字的判断,后续需要了解里面是如何实现的。然后还使用了stringbuilder类。这题比较复杂,首先是要去除多余的空格,然后再将整个字符串进行反转,然后再对单个单词进行反转。这里注意右指针的边界条件。暂时还没有做,后续补上。

2024-03-27 23:50:04 138

原创 代码随想录第六天|四数相加II |赎金信 |三数之和|四数之和

该题与两数之和类似,由于结果只要返回符合条件的元组数,所以可以将四个数组看成两个大组,用一个map来记录两个大组中两个数组所有元素的可能的和以及出现的次数,然后再通过两个for循环来遍历另外一个大组中的两个数组元素,与map中记录的和进行相加,若相加等于target值,则返回map中记录的次数。这里使用哈希数组映射ransomNote中的字母,与magazine字符串进行判断,若ransomNote中的字母在magazine字符串中出现过,则将该位置减1.最后若哈希数组中所有元素为0,则符合条件。

2024-03-26 22:39:35 195

原创 代码随想录第五天|有效的字母异位词 |两个数组的交集|快乐数|两数之和

判断完字符串长度相等后,需要统计两个字符串中字符出现的次数,在涉及到判断一个元素是否出现过以及出现过几次的问题时,使用哈希法,这里字符是小写字符,一共26个字母,以'a'的ASCII码值为基准,将其余字符与'a'相减,结果一定在0-25中,这里是有限个结果,所以可以用数组进行解决。但是本题需要返回的是索引,不是元素值,而计算需要用到元素值,这里有两个量,于是使用哈希结构中的hashmap,先遍历读取数组,将索引和元素放入map中,每读一个元素判断一次target-元素是否在map中出现过。

2024-03-25 22:37:43 375

原创 代码随想录第四天|两两交换链表节点|删除链表的倒数第N个节点 |链表相交|环形链表II

这里由于链表长度不一样,所以两个链表的起点指针要在相同位置上,后面才能有相遇的机会。所以首先要将短的链表与长的链表后端对其,将长链表起点指针移到短链表起点指针相同位置,然后以相同速度遍历链表,直到找到相遇节点。解决该问题一个巧妙的办法就是使用快慢指针,快指针先出发,慢指针后出发,若有环,则在慢指针进入环中后快指针一定会追上慢指针。解决该题的关键在于要知道交换节点或者进行删除添加节点操作时,当前指针要指向目标节点的前一个位置,同时配合使用虚拟头节点就能完美解决。删除链表的倒数第N个节点。

2024-03-24 15:19:40 157 2

原创 代码随想录第三天|删除链表元素|设计链表|反转链表

链表原地操作需要考虑的问题就是头结点的删除,在这里有一个比较巧妙的方法,在删除元素的时候先判读是否是删除头结点元素,若是,则将头结点向后移动即可。其他操作没有特殊的地方,就是将要删除结点的上一个结点的next指向要删除结点的下一个结点。删除链表元素有两种方法,一种是链表原地操作,还有一种是虚拟头结点解法,更推荐虚拟头结点解法,在后续的链表问题中,虚拟头结点的方法用的更多。使用虚拟头结点法的话,设置一个遍历指针指向虚拟头结点,则在删除头结点的时候和删除一般结点的操作是一致的,免去了讨论的麻烦。

2024-03-22 21:45:12 246 1

空空如也

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除