
力扣刷题
以刷题为主,锻炼自己的算法和数据结构的能力。
主要是为了自己以后遗忘了算法可以回来看,但是如果在这个过程中能帮助其他的人话那就是意外之喜了。
北原春希_
喜欢陈奕迅
展开
专栏收录文章
- 默认排序
- 最新发布
- 最早发布
- 最多阅读
- 最少阅读
-
自己对kmp算法的理解,借由 28. 实现 strStr() 为例
✔做题思路 or 感想 :就借由这道题来理解一下kmp算法吧kmp算法的操作过程我觉得有句话很合适 :KMP 算法永不回退 目标字符串 的指针 i,不走回头路(不会重复扫描 目标字符串),而是借助 next 数组中储存的信息把 模板字符串 移到正确的位置继续匹配kmp算法的重要点是计算next数组i的含义是指向后缀末尾位置的下标,j的含义是指向前缀末尾位置的下标和最大前后缀和...原创 2022-03-24 20:53:00 · 88 阅读 · 0 评论 -
115. 不同的子序列【动态规划】【大彻大悟包教包会】
✅做题思路or感想这道困扰我一刷好久的题终于在二刷的今天彻底理解了,通透啊!这道题的难点在于递推公式和初始化首先可以把题目按照自己的意思更大白话的复述一遍题面:找 s的子序列中t出现的次数复述:在s中挑选字符来组成t,求这个操作有几种方法dp数组含义dp[i][j]表示[0, i - 1]和[0, j - 1]的区间上的挑选字符使之匹配的方法个数💡递推公式这里从最后一步开始思考。以s = baba,t = ba为例子,当最后一个字符a相同时,有两种选择(从最后一步思考)s最后一原创 2022-04-09 18:55:43 · 253 阅读 · 0 评论 -
583. 两个字符串的删除操作【动态规划】【包教包会】
✅做题思路or感想同是一刷没有理解透彻的题,二刷终于理解透了。字符串匹配的题都要用最后一步的思考角度去思考,从最后部分开始思考dp数组含义dp[i][j]是从下标0开始长度为i和长度为j的两个字符串做到相同所需的最小步数💡递推公式从最后一步思考,以单词A和单词B为例,从完整的A和B的匹配思考当A的最后一位和B的最后一位不匹配时,有三种做法:反正A的最后一位和B的最后一位在一起已经用不了了,所以要么删A,要么删B,要么俩一起删了,就是不能让他俩最后一位在一起删A,则有dp[i][j] = dp原创 2022-04-09 19:49:27 · 315 阅读 · 0 评论 -
72. 编辑距离【动态规划】【超详细,包教包会】
✅做题思路or感想同是一刷没有理解透彻的题,二刷终于理解透了。字符串匹配的题都要用最后一步的思考角度去思考,从最后部分开始思考dp数组含义dp[i][j]是从下标0开始长度为i和长度为j的两个字符串做到相同所需的最小操作(亦可以理解成word1前 i个字符和word2前j个字符做到相同所需的最小操作数)💡递推公式从最后一步思考,以单词A和单词B为例,从完整的A和B的匹配思考当A的最后一位和B的最后一位不匹配时,有三种做法:对A删除:把A的最后一位删除掉,则有dp[i][j] = dp[i -原创 2022-04-09 20:25:07 · 238 阅读 · 0 评论 -
647. 回文子串【暴力解法】【动态规划】【绝对包教包会的终极详细】
✅做题思路or感想暴力解法用双指针法判断是否回文,用两个for遍历出所有子字符串即可class Solution {public: bool isGood(const string &str) { int left = 0, right = str.size() - 1; while (left < right) { if (str[left] != str[right])return false;原创 2022-04-09 21:38:29 · 298 阅读 · 0 评论 -
516. 最长回文子序列【动态规划】【绝对包教包会,自信】
✅做题思路or感想子数组是连续的,子序列是不连续的这一题动态规划的难点在于推导递推公式,以及许久未见过的遍历顺序dp数组含义dp[i][j]表示字符串s在[i, j]上的最长回文子序列💡递推公式字符串问题都要从最后一步的角度去分析。比如字符串有8个字符,不能从第一个字符到第二个字符这样分析,要从8个字符的情况分析,然后再到7个,6个这样由大向小分析若s[i] = s[j],说明主串的[i, j]部分的外围符合了回文子序列的要求,可以向外拓展两个位置,故有之前的子序列最大长度拓展两个长度原创 2022-04-09 23:21:19 · 404 阅读 · 0 评论 -
二叉树的遍历
二叉树的遍历前序遍历遍历顺序:中,左,右代码实现:void dfs(TreeNode* root) { if (root != nullptr)result.push_back(root->val); if (root->left != nullptr)dfs(root->left); if (root->r...原创 2022-03-26 13:48:00 · 207 阅读 · 0 评论 -
110. 平衡二叉树
✅做题思路or感想:用递归后序遍历二叉树,然后从底部开始记录高度为0,然后往上加1。每一次操作节点的时候比较左右子树的高度,如果有一棵树不符合条件,则直接把-1返回到最顶的根节点class Solution {public: int getDepth(TreeNode* cur) { if (cur == nullptr)return 0; //节点触...原创 2022-03-28 22:44:00 · 66 阅读 · 0 评论 -
257. 二叉树的所有路径
✅做题思路or感想:直接遍历二叉树,然后用一个字符串记录一条遍历路径,然后遍历到叶子节点的时候就把字符串加入result里就好了class Solution {public: vector<string> result; //存答案 void dfs(TreeNode* cur, string str) { if (!cur->le...原创 2022-03-28 22:47:00 · 229 阅读 · 0 评论 -
111. 二叉树的最小深度
✅做题思路or感想:直接递归到叶子节点,然后更新最小值就好了这不是和上一题一模一样吗class Solution {public: int result = 99999; void dfs(TreeNode* root, int sum) { if (root->left == nullptr && root->right ...原创 2022-03-27 10:33:00 · 72 阅读 · 0 评论 -
104. 二叉树的最大深度
✅做题思路or感想:直接递归到叶子节点,然后更新最大值就好了class Solution {public: int result = 1; void dfs(TreeNode* cur, int sum) { if (cur->left == nullptr && cur->right == nullptr) { //递归到叶...原创 2022-03-27 10:24:00 · 210 阅读 · 0 评论 -
106. 从中序与后序遍历序列构造二叉树
✅做题思路or感想:这道题要从前中后序遍历的特点入手。因为后序遍历的最后一个节点必是根节点,故从次开始如果数组长度为0,则说明是空节点如果数组不为空,那么后序数组的最后一个元素作为节点元素找到后序数组的最后一个元素在中序数组中的位置,作为切割位置利用切割位置把中,后序数组切成左子树的中,后序数组和右子树的中,后序数组递归左子树和右子树class Solution {p...原创 2022-03-28 22:59:00 · 84 阅读 · 0 评论 -
105. 从前序与中序遍历序列构造二叉树
✅做题思路or感想:根据前序遍历找根节点由前序遍历根节点的值来切割中序数组,再由中序数组切割前序数组,最终切割成左子树的中序,前序数组和右子树的中序,前序数组。递归造根节点的左子树和右子树class Solution {public: TreeNode* buildTree(vector<int>& preorder, vector<int>...原创 2022-03-29 20:19:00 · 100 阅读 · 0 评论 -
112. 路径总和
✅做题思路or感想:也是遍历一遍二叉树的路径,每次遍历一个节点就把targeSum减去对应的节点值,如果最后是叶子节点并且targeSum为0,则符合条件class Solution {public: bool flag = false; void dfs(TreeNode* cur, int sum, int targetSum) { //判断条件 ...原创 2022-03-28 22:50:00 · 71 阅读 · 0 评论 -
113. 路径总和 II
✅做题思路or感想:也是遍历一遍二叉树,判断路径总和和是否是叶子节点,要注意的是这里还需要加一个vector来记录路径class Solution {public: vector<vector<int>>result; void dfs(TreeNode* cur, vector<int>vec, int sum) { ...原创 2022-03-28 22:53:00 · 233 阅读 · 0 评论 -
235. 二叉搜索树的最近公共祖先
✅做题思路or感想:递归一条边的写法:if (dfs(root->left))return;if (dfs(root->right))return;搜索整棵树的写法left = dfs(root->left);right = dfs(root->right);//left与right的逻辑处理在递归函数又返回值的情况下:如果搜索一条边,那么...原创 2022-03-30 16:18:00 · 162 阅读 · 0 评论 -
236. 二叉树的最近公共祖先
✅做题思路or感想:这道题教会了我一个很重要的点:当递归函数有返回值时,遍历二叉树的方法论递归一条边的写法:if (dfs(root->left))return;if (dfs(root->right))return;搜索整棵树的写法left = dfs(root->left);right = dfs(root->right);//left与rig...原创 2022-03-30 12:25:00 · 71 阅读 · 0 评论 -
501. 二叉搜索树中的众数
✅做题思路or感想:直接用map来记每一个节点值的出现次数,然后输出最高次数的节点值就好了class Solution {public: unordered_map<int, int>HashMap; int result = 0; void dfs(TreeNode* root) { if (root == nullptr) retur...原创 2022-03-30 10:53:00 · 75 阅读 · 0 评论 -
101. 对称二叉树
✅做题思路or感想:这题是要同时遍历左子树和右子树遍历左子树的外侧和右子树的外侧遍历左子树的内侧和右子树的内侧最后判读是否外侧和内侧都是对称的class Solution {public: bool dfs(TreeNode* left, TreeNode* right) { //处理左右节点有空节点的情况,实际上也是处理递归到尽头时的情况,到尽头是...原创 2022-03-27 10:15:00 · 73 阅读 · 0 评论 -
226. 翻转二叉树
做题思路or感想:遍历一遍二叉树,然后将遍历节点的左右节点互换就好了class Solution {public: void dfs(TreeNode* root) { if (root == nullptr)return; swap(root->left, root->right); //交换左右节点 dfs(roo...原创 2022-03-27 09:59:00 · 72 阅读 · 0 评论 -
102. 二叉树的层序遍历
二叉树的层序遍历(bfs)✅做题思路or感想:利用队列来实现层序遍历当明确每一层直接的元素不用区别对待时,其实代码中的size可以不写,但在这里要根据每一层来进行分组,所以要写size当队列为空时,结束bfsclass Solution {public: vector<vector<int>> levelOrder(TreeNode* root) ...原创 2022-03-26 14:03:00 · 234 阅读 · 0 评论 -
98. 验证二叉搜索树
✅做题思路or感想:对于二叉搜索树,用中序遍历时,二叉树的节点值是递增的对于二叉搜索树,用中序遍历时,二叉树的节点值是递增的对于二叉搜索树,用中序遍历时,二叉树的节点值是递增的我真是服了我怎么老是忘记啊故这里的思路就是判断是不是递增了,懂了上面的话后就相当简单了class Solution {public: vector<int>result; //记录二叉搜索...原创 2022-03-29 21:11:00 · 67 阅读 · 0 评论 -
530. 二叉搜索树的最小绝对差
✅做题思路or感想:对于二叉搜索树,用中序遍历时,二叉树的节点值是递增的对于二叉搜索树,用中序遍历时,二叉树的节点值是递增的对于二叉搜索树,用中序遍历时,二叉树的节点值是递增的虽然这里求的是树中任意两个不同节点的最小差值,但是由于二叉搜索树在中序遍历中是单调递增的,所以只需要比较当前节点和上一个节点的差值的绝对值就可以了class Solution {public: int ...原创 2022-03-29 21:22:00 · 232 阅读 · 0 评论 -
700. 二叉搜索树中的搜索
✅做题思路or感想:递归参数:一个遍历节点,一个比较节点值的val递归中止条件:cur == nullptr为止,即是节点遍历到了头单层递归逻辑:比较节点值和目标值如果相等,则给预设的节点赋值如果大了,就往左节点走如果小了,就往右节点走最后在主函数返回预设节点class Solution {public: TreeNode* result = nullptr;...原创 2022-03-29 20:46:00 · 73 阅读 · 0 评论 -
617. 合并二叉树
✅做题思路or感想:有返回值的递归果然还是特别不熟练啊递归参数:因为要同时遍历两棵树,所以要同时传入两棵树的节点!递归中止条件:当其中一个节点无的时候,就返还另一个节点(两个节点都无,就返回空节点)递归单层逻辑:两个节点的值相加(因为前面中止条件决定了这里的两个节点都必定不是空节点)有返回值的递归最后还要再把节点返回回去,太男了class Solution {public: ...原创 2022-03-29 20:32:00 · 62 阅读 · 0 评论 -
376. 摆动序列
✅做题思路or感想这题的思路源于力扣上的nwpuCfy,这位先生的思路可堪一绝这一题代码随想录上用的是贪心,但是我贪心太糟糕了,故这里选用动态规划来解这一题的dp的思路并不难,难的是怎么把这道题看成dp的题来做dp四部曲dp数组的意义dp[i]表示的是[0, i - 1]上最长的摆动序列递归公式当前面两个差值不是一正一负时,则dp[i] = dp[i - 1]当前...原创 2022-04-03 14:21:00 · 68 阅读 · 0 评论 -
78. 子集
✅做题思路or感想集合的经典问题,直接回溯法,递归三部曲。递归参数这里用一个startIndex来控制可选元素的范围,从而进行有效去重。这个做法老生常谈了递归终止条件这一题甚至不需要递归中止条件........单层递归逻辑用result来实时记录变化的temp就好了class Solution {public: vector<vector<int...原创 2022-04-02 19:00:00 · 74 阅读 · 0 评论 -
455. 分发饼干
✅做题思路or感想分饼干,经典贪心题这里的贪心策略是:用最小的饼干去满足食量最少的小孩or用最大的饼干去满足食量最大的小孩这里我用前者class Solution {public: int findContentChildren(vector<int>& g, vector<int>& s) { //必须先要给二者进行大小...原创 2022-04-03 13:30:00 · 91 阅读 · 0 评论 -
131. 分割回文串
✅做题思路or感想这题的主题有两个:分割字符串,检查是否回文难点在于第一点,这里用startIndex作为子串开始的地方,i作为子串结束的地方,用s.substr(startIndex, i - startIndex + 1)来分割出子串递归单层逻辑就是判断子串是否回文,如果回文,则加入vector<string>中,否则continueclass Solution {pu...原创 2022-04-02 17:29:00 · 68 阅读 · 0 评论 -
47. 全排列 II
✅做题思路or感想求排列问题,用回溯法这里和一般的排列问题的区别是:有重复的数字然后因为是求排列,则同一个位置上的数字不能重复用这就要求了:既要树层去重,又要树枝去重而这些操作只用一个used数组就可以了class Solution {public: vector<vector<int>>result; vector<int>te...原创 2022-04-02 20:24:00 · 70 阅读 · 0 评论 -
77. 组合
✅做题思路or感想:这道题用回溯的操作即可值得注意的是这里为了让子集都是递增的(如[2,4],[3,5])所以这里要有一个startIndex来控制元素的范围,使得下一个加入的元素一定比当前处理的元素大class Solution {public: vector<int>temp; vector<vector<int>>result;...原创 2022-04-01 11:03:00 · 67 阅读 · 0 评论 -
108. 将有序数组转换为二叉搜索树
✅做题思路or感想:构建二叉树的基本思想:找头节点,分割左右子树的序列二叉搜索树的找头节点很简单:中间的节点就是头节点,并且就可以就着中间节点进行分割左右子树的序列class Solution {public: TreeNode* sortedArrayToBST(vector<int>& nums) { //当序列为空,则证明这里应该造一个空...原创 2022-04-01 10:50:00 · 69 阅读 · 0 评论 -
90. 子集 II
✅做题思路or感想这道题仍然是用回溯,和普通的求集合的题有区别的地方是:集合中有相同的元素这里处理相同元素的做法是用一个used数组来做到树层去重,注意这种做法需要先对遍历的数组进行排序!!!!!!!递归三部曲:递归参数这里除了老生常谈的startIndex外,还要额外加一个used数组进行树层去重递归中止条件这道题没有甚么额外的限制条件,故这里并不需要画蛇添足的加上递归中止...原创 2022-04-02 19:22:00 · 74 阅读 · 0 评论 -
491. 递增子序列
✅做题思路or感想这一题依旧是子序列问题,用回溯法然而这道题在有相同元素的情况下还要求不同的递增子序列,这就代表了不能对原数组进行排序!,因此就不能像前面一样用used数组进行树层去重了我思来想去找不到更好的方法,只能靠用set强行去重来AC了,惭愧class Solution {public: vector<vector<int>>result; ...原创 2022-04-02 19:55:00 · 73 阅读 · 0 评论 -
39. 组合总和
✅做题思路or感想这里依旧是找组合,故依旧是用回溯法而因为这里的元素是可以重复选取的,所以这里的startIndex在递归时不需要+1,或者直接干脆不用startIndex就可以了但是为了防止[2,2,3],[2,3,2]这种重复,所以需要安排一下子集都是要递增的就好了class Solution {public: vector<int>temp; vect...原创 2022-04-01 12:18:00 · 211 阅读 · 0 评论 -
51. N 皇后
✅做题思路or感想(二刷直接初见过,在用时和内存消耗上远强于一刷,我真的成长了)经典八皇后问题,回溯法理所应当八皇后的要求:一个皇后的上下左右,以及斜线上不能有其他皇后故这里的思路就是判断当前位置是否符合八皇后的要求,符合,则回溯递归,不符合,则continue递归三部曲递归参数除了地图和地图大小要传入外,这里还需要用row来代表现在递归进行到的哪一行了,这里的妙处是这样做可以直...原创 2022-04-02 21:01:00 · 94 阅读 · 0 评论 -
46. 全排列
✅做题思路or感想排列问题,一眼回溯法排列问题注重元素间的排序,而集合问题不用。故这里并不需要startIndex来进行控制元素取值范围,而是需要用used数组来记录元素是否使用过,避免一个元素的多次使用递归三部曲递归参数用一个used数组来记录使用记录递归中止条件当temp和原数组等大时,就可以收网了递归单层逻辑判断元素是否使用过,若没用过,则加入temp中c...原创 2022-04-02 20:08:00 · 71 阅读 · 0 评论 -
701. 二叉搜索树中的插入操作
✅做题思路or感想:这里的插入值的操作不是在节点和节点直接插一个新节点,而是在老的二叉树的末尾新增节点。。。故这里直接利用二叉搜索树的特性直接找新节点位置就好了值得注意的是这里是需要让前一个节点链接新节点,也就是存在父子节点之间的赋值操作,所以这里要记录上一个节点!!!class Solution {public: //这里要多一个参数:记录上一个节点 void dfs...原创 2022-03-30 16:55:00 · 114 阅读 · 0 评论 -
669. 修剪二叉搜索树
✅做题思路or感想:这道题的主旋律是:将节点值控制在[low, high]中这里因为会有删减的操作,所以还是要有父子节点间的赋值,故要用有返回值的递归函数比较方便,且因为要修改一整棵树,所以说要遍历整棵树首先要明确带返回值的递归函数的代表意义,这里的递归函数表示的是修改好的搜索二叉树的头节点class Solution {public: //明确递归函数的意义:修改好的头节点...原创 2022-04-01 10:32:00 · 69 阅读 · 0 评论 -
450. 删除二叉搜索树中的节点
✅做题思路or感想:在删除一个节点的时候可能有以下情况找不到节点,那么就之间返回最开始的树就好了找到了节点节点是叶子节点,则直接删掉就好了节点一边是空的,另一遍是有子树的,则直接把该节点的子节点返回给该节点的前一个节点,然后把这个节点删除节点两边都是非空的,则把节点的左子树接到右子树的最左面(因为左子树的数值一定全部小于右子树的数值,而右子树的最小值就是右子树最左面的值,所以要把...原创 2022-03-31 14:35:00 · 182 阅读 · 0 评论