![](https://img-blog.csdnimg.cn/20201014180756918.png?x-oss-process=image/resize,m_fixed,h_64,w_64)
算法
文章平均质量分 70
TonyPaPa
这个作者很懒,什么都没留下…
展开
-
leetcode978 最长湍流子数组 中等
题目:题目链接思路:我使用动态规划的做法题目提供了两种方案,那么每一步都考虑用哪种方案最好,使用两个dp数组记录当前位置i的最长湍流子数组长度以实例1为例:9>4且9在偶数位置上所以优先考虑方案2,所以方案1是不符合的,为1,故two[i] = 2, one[i] = 14>2且4在奇数位置上所以优先考虑方案1,所以方案2是不符合的,为1,此时方案1要考虑前一个数的最长湍流子数组长,其值+1与2比较谁大,谁大dp[i]就等于谁,因为要求最长,所以要看前面的位置能不能和当前位置连起原创 2020-08-14 17:02:44 · 113 阅读 · 0 评论 -
leetcode673 最长递增子序列的个数 中等
题目:思路:先来回顾动态规划求最长递增子序列长度 //动态规划 static int lengthOfLIS(int[] nums) { if(nums == null || nums.length == 0){ return 0; } //整个问题的最优解,一开始至少有一个 int maxLen = 1; int[] dp = new int[nums.length];原创 2020-08-12 13:25:53 · 147 阅读 · 0 评论 -
网易互联网8.8笔试 第三题 背包问题 回溯
题目:思路:简单思考后可以想到一个回溯的做法考虑每个物品是给第一个人还是第二个人还是丢掉答案的最差解是所有物品都丢弃看到代码后会觉得竟如此简单代码:public class Main { /** * one 给第一个人 * two 给第二个人 * res 结果,一开始为全部的和,因为最差的解就是所有都丢弃 * left 剩下的物品价值 */ static int one, two, res, left; public原创 2020-08-09 17:17:17 · 254 阅读 · 0 评论 -
Leetcode61 旋转链表 中等
题目:思路:仔细思考后旋转链表其实就相当于链表有个环,旋转后改变了头结点而已。接下来可以找到一个关系,以题目示例1为例假设5的next-1,也就是有一个环,那么移动后的头结点有什么规律移动1,新头结点=倒数第一个=正数第5个移动2,新头结点=倒数第二个=正数第4个移动3,新头结点=倒数第三个=正数第3个移动4,新头结点=倒数第四个=正数第2个移动5=没移动可以发现,新头结点=原链表正数第(链表长-移动步数+1)个那么只需要头结点正向移动(链表长-移动步数)个就能到达新头结点总结:原创 2020-08-08 14:13:07 · 191 阅读 · 0 评论 -
leetcode 面试题04.09 二叉搜索树序列 困难
题目:思路:首先明确的一个点:根结点的顺序是不会变的!!变的是孩子结点的顺序再思考可以怎么变顺序,注意搜索树的性质!!要保证树是一样的,那么结点大小相关关系就不能变比如:当确定了6和10后,下一层无论那个结点进来构建树,都能找到正确的位置都不会造成影响,这就是相对关系序列问题,自然想到回溯法如何保证相关关系?用一个队列来保存再配合回溯。代码中关键部分都有注释代码:/** * Definition for a binary tree node. * public class Tre原创 2020-08-05 23:42:07 · 237 阅读 · 0 评论 -
剑指Offer 牛客 JZ17 树的子结构 较难
题目:题目链接思路:首先先找出A树中有没有B的根结点,如果没有,直接返回false。注意,A是二叉树,不是搜索树,所以key有可能是会重复的,所以要把所有值和B根结点相同的结点保存起来接下来判断是否是子结构:联想到二叉树的镜像递归做法,用递归判断同方向的结点值是否相等注意点!!因为判断的是子结构,有可能出现判断完后,A树的孩子结点并不是null的情况,所以递归结束条件要稍加修改代码:public class Solution { public class TreeNode {原创 2020-08-05 12:06:18 · 181 阅读 · 0 评论 -
剑指Offer 牛客 JZ65 矩阵中的路径 较难 递归
题目:题目链接思路:矩阵中找一条路径,使用嵌套循环假设每个位置都是一个起点求解是否存在路径:使用递归,根据题目描述,每一步可以走4个方向,所以4个方向都走,判断是否有解有解的条件:1.当前值和要寻找的值相等且当前值未被访问过, 2.当前值是最后一个要寻找的值有了以上思路,很快可以写出递归,注意递归结束条件以及可以适当“剪枝”递归结束条件需要判断当前位置是否越界剪枝的内容包括只要有任意一个方向有解,即可返回true,不需要继续求解因为题目不要求求所有路径综上,使用一个bool二维数组表示原创 2020-08-03 18:33:47 · 126 阅读 · 0 评论 -
剑指Offer 牛客 JZ61 序列化二叉树
题目:public class TreeNode { int val = 0; TreeNode left = null; TreeNode right = null; public TreeNode(int val) { this.val = val; }}思路:这里我选择先序遍历进行一个序列化,因为考虑到反序列化的时候,如果序列化是按先序的那么序列化后面的结点是前面结点的孩子结点,这样再去考虑递归好不好做反序列化代码:序列化的原创 2020-08-03 16:52:42 · 183 阅读 · 0 评论 -
剑指Offer 牛客 JZ25 复杂链表的复制
题目:思路:题目要求深拷贝,那就不用用另外的指针指向原引用了,必须有new RandomListNode()思考如何保存原链表节点顺序信息。我个人对原题目的理解:不确定有没有下面这种情况无论怎么样,都需要保存原链表节点顺序信息,联想到HashMap,key为原引用,value为新节点用HashMap的一个好处,因为每个节点的唯一性,所以每个节点引用也是唯一的,当next,random指向同一节点的时候,保存节点顺序信息时不会有重复项代码:public class Solution {原创 2020-07-31 16:34:10 · 173 阅读 · 0 评论 -
剑指Offer 牛客JZ1 二维数组中的查找 较难
题目:思路:一看见有序查找,自然而然想到二分搜索,但题目给的条件还可以进一步优化。1.因为每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序,所以左上角和右下角分别是二维数组的最小值和最大值,这样可以在寻找前先简单比较,如果小于最小值或大于最大值直接返回false2.同样因为有序,所以每一行的二分搜索并不需要从头到尾,而是可以根据上一行的搜索结果来判断。如:我的二分搜索找的是第一个大于等于目标值的数的下标,如果找到了这样一个数,那么下一行的二分结尾直接可以=当前找到下标-1,原创 2020-07-29 17:59:22 · 168 阅读 · 0 评论 -
剑指Offer 牛客 35 数组中的逆序对
题目:思路:题目告诉数据范围明显说明暴力法是A不过这道题的,所以采用归并排序的做法来做。归并排序的做法这里不赘述了,不会的自行去复习。归并的同时计算逆序对数这里注意一点!!归并的过程用for是超时的,要用while的做法代码:public class Solution { public int count = 0; public int InversePairs(int [] array) { if (array == null || array.lengt原创 2020-07-28 18:06:33 · 93 阅读 · 1 评论 -
剑指offer 牛客 JZ46 孩子们的游戏(圆圈中最后剩下的数)
题目:题目链接思路:只要给定小朋友人数n和m,那么结果就是确定的。这里我使用递归的方法。函数f(n, m)表示最终剩下的小朋友的序号。解释这句话!!最终剩下的小朋友是确定的且唯一的(给定n, m就确定了),而序号是会变化的,因为每一次去掉一个小朋友都从上一次去掉的下一个开始,所以序号会变如何根据f(n-1, m)求f(n, m)?每次都去掉第m%n 个小朋友,所以下一次从序号为 m%n 开始。如果知道了下一次f(n-1, m)最终剩下的小朋友序号为k,那么本次f(n, m)该小朋.原创 2020-07-28 14:06:18 · 141 阅读 · 0 评论 -
剑指offer 牛客 JZ28 数组
题目:思路:这里讲最优解,时间复杂度O(n),空间复杂度O(1)使用hash的做法就不讲了,比较容易,它的时间复杂度是O(n),空间复杂度 O(n)最优解:把问题想成一个候选数和血量,什么意思?如果血量=0,说明没有候选数,则当候选数为前遍历到的数如果血量!=0,说明有候选数,则比较当前数与候选数是否相等,如果不等,则把当前数和一个候选数都删掉,删掉候选数做法为血量-1遍历完数组,判断血量是否=0,=0没有一个数的个数超过数组长度的一半,返回0!=0,再次检查该数的个数是否超过数组长度的原创 2020-07-25 12:08:53 · 123 阅读 · 0 评论 -
剑指offer 牛客 47 递归
题目:题目思路:看到题目要求第一反应是二进制位运算及递归。原本想用位运算来做,但我思路中仍然使用到了while,所以最终使用递归来做。递归不可以使用if,那么改用&&操作来替代递归中0的判断,利用&&前一个条件判断为false,不执行后一个条件的语法,前一个条件判断是否为0代码:public class Solution { public int Sum_Solution(int n) { int sum = n; boo原创 2020-07-24 13:06:20 · 95 阅读 · 0 评论 -
剑指offer 牛客 JZ47 不用加减乘除做加法
题目:思路:既然不能用加减乘除,那很明显就要使用位运算了先举几个例子感受位运算如何进行加法(二进制)加法异或^与&0, 0000, 1101, 0101, 101通过上表观察发现:如果单纯做异或,有可能得到不正确的结果,但又返现与操作表示了进位信息,做加法=不管进位的加法+进位=正确结果,这个做法每个位置都如此这里与操作的进位信息要进行一下处理,进行左移1位,这样进位信息与需要进位的位置重合如表格中,1+1的进位信息二进制原创 2020-07-24 11:10:22 · 157 阅读 · 0 评论 -
剑指offer 牛客JZ67 剪绳子 动态规划
题目:分析:这个题目跟leetcode上的几道题目很像,都是一种组合问题可看我的两篇博客第一篇第二篇本题要求组合成targer的组合数中乘积最大的,用动态规划记录下求过的值。动规数组表示的意思, dp[i]表示i这个数的所有组合中乘积最大是多少,子问题是什么,使用当前一个数字作为组合后,剩下的值的所有组合中乘积最大是多少注意有几个特殊情况!!当target <= 4的时候,(不包括1,因为题目要求切分段数m>1,m <= 长度target,自然猜测题目会以1进行输入),原创 2020-06-29 22:54:57 · 160 阅读 · 0 评论 -
leetcode354. 俄罗斯套娃信封问题(最长递增子序列的应用) 困难
题目:分析:这是一道解法很骚的题目,是最长递增子序列的应用直接说解法,先进行排序,长度升序,高度降序排序然后把高度全去下来找最长递增子序列这么做的正确性:首先套信封是严格长和高都要小于才能套进去的,不能等于找到最长递增子序列的正确性在于,那么长度必定不相等,因为如果长度相等,那么按高度降序排序,不可能出现递增,那么只要出现递增,那么前一个的长度必定小于后一个,能套进信封代码:class Solution { public int maxEnvelopes(int[][] enve原创 2020-06-25 21:36:06 · 217 阅读 · 0 评论 -
首尾指针法简单小结
以一道题目的优化过程来浅显的说一说首尾指针法这是一道leetcode的题目我之前的博客记录过博客中我的做法就是比较常规的记录每个位置的左右最大值1.第一种优化只用一个数组记录每个位置右边最大值,不记录左边最大值,左边最大值用一个变量来记录即可,这样节省了空间,其他步骤相同2.第二种优化,使用首尾指针大体逻辑延续上面的做法,首尾两个位置是不可能有雨水装的。首尾指针怎么做,逻辑如下:分别记录左右指针左右两边的当前最大值,然后每次解决左右最大值中的较小值并移动左或右指针。为什么能这么做(正确性原创 2020-05-24 10:17:27 · 907 阅读 · 0 评论 -
算法 单链表删除重复元素
1.删除重复的元素,保留一个leetcode题目代码:/** * Definition for singly-linked list. * public class ListNode { * int val; * ListNode next; * ListNode(int x) { val = x; } * } */class Solution { ...原创 2020-05-04 12:12:34 · 3812 阅读 · 0 评论 -
leetcode 240. 搜索二维矩阵 II 中等 矩阵
题目:分析:条件每行从左到右有序和每列从上到下有序很关键,怎么高效的搜索出来呢?一个很巧妙的想法,可以从两个底角出发(左下角或右下脚),这里以左下角为例,因为是有序的,所有每一行右边的数比当前位置大,每一列上面的数比当前位置小以底角为出发点,值比目标小,则往右走,值比目标大,则往上走(为什么不往左走?一可以理解成是从左边走过来的二是如果大了往右,小了往左不就永远在一行里面了吗,在做无用功)...原创 2020-04-25 21:42:36 · 145 阅读 · 0 评论 -
leetcode 738. 单调递增的数字 中等 贪心
题目:分析:如何找到一个小于或等于N的最大整数,并且各个位数上的数字时单调递增的。很容易想到的一个思路是后部分用尽量多的9,前一部分数值最大,这样拼在一起就可以得到一个小于或等于N的最大整数剩下的问题就是如何找到9的开始位置,考虑条件各个位数上的数字要单调递增,那么如果能找到那个不再递增第一次下降的位置,从这个位置开始往前逐一减小前一个位置的大小,直到当前位置不小于前一个位置就停下来,再从停...原创 2020-04-25 15:33:01 · 196 阅读 · 0 评论 -
leetcode 96. 不同的二叉搜索树 中等 动态规划
题目:分析:考虑使用动态规划的做法,1-n作为结点的二叉搜索树。先总结二叉搜索树的特点,搜索树按照节点大小将节点分到左或右子树相应位置并且左子树小于右子树对题目的思考:二叉搜索树有多少种这种文法有点类似排列组合问题,有多少种二叉搜索树的排列组合,那么根结点就可以是1-n任意一个,剩下的问题就是子问题,子树有多少种排列组合,再结合二叉搜索树的上述特点很容想到动态规划的做法数组dp保存i个节...原创 2020-04-25 11:27:42 · 186 阅读 · 0 评论 -
leetcode 650. 只有两个键的键盘 中等 动态规划
题目:分析:这个题目做法上不太好理解,总体分为这个数是质数还是不是质数,如果是质数,那么只能一个一个字符复制不然不可能恰好n个A;如果不是质数,那么可以进行乘法因子拆分减少粘贴复制次数代码:class Solution { public int minSteps(int n) { int[] dp = new int[n+1]; dp[1] = 0...原创 2020-04-24 22:27:07 · 169 阅读 · 0 评论 -
算法 回溯求排列组合,子集问题的总结
leetcode上有许多用回溯求排列组合,子集的题目leetcode46leetcode47 我的思路可看这里leetcode77 我的思路可看这里leetcode39leetcode40leetcode216leetcode78leetcode90 我的思路可看这里总结一下用回溯法求这类排列组合,子集问题基本模型都是几乎一样的(看我的思路里面也有代码),只需要根据实际题目稍...原创 2020-04-24 17:27:16 · 263 阅读 · 0 评论 -
leetcode 90. 子集 II 中等 回溯
题目:分析:题目要求出所有可能的集合,首先不要被这个条件吓到,和用回溯求排列的模型都是一样的只不过需要修改一些细节而已(回溯求全排列可看这里)求出所有子集主需要把大小传进去即可,和一般回溯求法没什么太大不同需要注意的点,观察示例发现,[1,2],[2,1]这样的算重复,接下来就是解决重复问题总结一个方法当原序列含重复项的时候,先进行一个排序当结果子集不能如[1,2],[2,1]重复...原创 2020-04-24 17:14:50 · 163 阅读 · 0 评论 -
leetcode 77. 组合 中等 回溯
题目:分析:日常生活也会遇到的问题,数的思路是确定第一个数->考虑后面的所有组合情况,然后第一个数换一个->考虑后面的所有组合情况。接下来思考一个问题,是不是每个数都有机会做第一个数,答案是不一定,取决于每个组合中的个数是多少。以题目示例为例,组合中的个数是2,也就是说1-4里面4是不可能当第一个数的,因为它是末尾的数,后面没有多的数了,而不可能与前面的数组合因为这些组合之前已经...原创 2020-04-23 22:57:00 · 177 阅读 · 0 评论 -
leetcode 47. 全排列 II 中等 回溯
题目:分析:题目进行了改进,多了一个条件,原序列可能包含重复的数字,这个时候再来求所有不重复的全排列。与原序列回溯相比,必定会多一个判定条件用于剪枝,而且这个判定条件一定是用于判定是否重复的,如何思考呢。先回想一下这个回溯法的过程(步骤),现在假设原序列是不含重复数字的,回溯法就像人工求全排列一样,先确定第一个位置的数字,然后考虑剩下位置的全排列,然后更换第一个位置的数字再求剩下位置的全排列...原创 2020-04-23 22:23:00 · 190 阅读 · 0 评论 -
leetcode 547. 朋友圈 中等 深度优先搜索
题目:分析:根据题目很容易想到无向图的深度优先搜索,其实这个朋友圈的也就是深度优先搜索问题因为条件说了朋友具有传递性代码:class Solution { public int findCircleNum(int[][] M) { boolean[] marked = new boolean[M.length]; int circle = 0; ...原创 2020-04-23 21:00:58 · 214 阅读 · 0 评论 -
算法 子串类问题总结 Java实现
1.公共子串可不连续1.最长公共子序列,可看这道题目,使用动态规划的做法2.判断一个字符串是否是另一个的子序列static boolean isSubString(String s, String t){ int i = 0; int j = 0; while(i < s.length() && j < t.leng...原创 2020-04-12 10:37:11 · 230 阅读 · 0 评论 -
leetcode 120. 三角形最小路径和 中等 动态规划
题目:分析:注意理解题目的一点是每一步只能移动到下一行中相邻的结点上,这句话意思是只能向下移动或右下移动,而不能向左下移动很显然使用动态规划的思想,我这里使用的是最简单想到的自顶向下,用一个二维数组记录状态,记录每一个位置(走到当前位置)的最小路径和,那么最优解出现在二维数组的最后一行中动态规划的做法:遍历每一行,对于每一行而言,每个位置的来源来自正上方或左上方有两个特殊的点要注意,每一...原创 2020-04-11 16:33:20 · 150 阅读 · 0 评论 -
leetcode 524. 通过删除字母匹配到字典里最长单词 中等 字符串
题目分析:注意题目条件,首先满足长度最长的字符串,其次要字典顺序最小也就是涉及到了字符串的大小比较(长度相同下就要比较字典顺序,这个字典顺序不是题目给的那个“字典”,而是ASCII码顺序)。可以通过删除给定字符串的某些字符来得到字典里的字符串,也就是说是一个不连续子串问题,字典里的字符串是否是给定字符串的一个不连续子串循环比较每个字典中的字符串,判断是否是给定字符串的子串及记录最长长度和字...原创 2020-04-10 23:57:19 · 163 阅读 · 0 评论 -
leetcode 680. 验证回文字符串 Ⅱ 简单 双指针
题目:分析:从回文字符串特点出发,有一个中间点,中间点两边的字符成镜像,逐一相等(不管字符串长度是奇数还是偶数)。利用这个特点,可以使用双指针分别指向一头一尾,同时进行移动判断字符是否相等,如果不等,考虑删除任意字符再进行判断剩余的是否是回文字符串代码:class Solution { public boolean validPalindrome(String s) { ...原创 2020-04-10 22:36:56 · 119 阅读 · 0 评论 -
leetcode 9. 回文数 简单 整数
题目:分析:很容易想到转为字符串来判断是否是回文字符串,但进阶要求不能转为字符串,接下来就思考怎么用整数判断是否是回文回文的特点都是从中间切开,左右两边成镜像,也就是后半部逆序后等于前半部。后半部逆序怎么做?每次把原整数的末尾取下来(原整数会变小),下一次计算前先把后半部分乘10再加上本次的末尾。如何判断已到中间了?原整数不再大于后半部分,这时候就到中间了,因为整数判断大小可通过位数判断...原创 2020-04-06 17:19:52 · 167 阅读 · 0 评论 -
leetcode 647. 回文子串 中等 字符串
题目:分析:题目要求求出所有的回文字符串的个数,思考回文字符串的特点,有一个中心,并且两边字符相等,还有一个特点,回文字符串的长度可能是奇数也可能是偶数假设每个字符都是一个回文字符串的中心,向两边扩展看有多少个回文字符串代码:class Solution { int count = 0; public int countSubstrings(String s) { ...原创 2020-04-06 16:58:34 · 102 阅读 · 0 评论 -
leetcode 205. 同构字符串 简单 字符串
题目:分析:同构的意思是字符串结构相等,而字母不必相等,那么只要逐个字符判断上次出现的位置在两个字符串中是否相等即可代码:class Solution { public boolean isIsomorphic(String s, String t) { if(s.length() != t.length()){ return false;...原创 2020-04-06 16:37:04 · 102 阅读 · 0 评论 -
leetcode 409. 最长回文串 简单 字符串
题目:分析:首先不要被题目吓到要求最长回文子串,其实只需要把长度求出来即可,不需要求出串是什么。先来理解回文字符串的特点,以字符串中间为中点分开两边,两边的字符串是镜像的,并且在这道题里最重要的一点是两边的字符是完全相等的,也就是说字符个数必定是偶数,还有一种情况,回文字符串长度是奇数,那就是说中间点的那个字符只出现一次,其余字符仍符合个数必定是偶数。总结,回文字符串至多只有一个字符是奇数...原创 2020-04-06 16:22:34 · 136 阅读 · 0 评论 -
leetcode 128. 最长连续序列 困难 Set
题目:分析:根据题目意思,这次要找到数值上连续的最长序列长度,并不要求位置连续,想到了用hashmap统计每个元素的个数以应对重复元素的情况,但后来发现错了,重复元素的情况不能算作连续既然重复元素不算,那么去重即可,去重自然想到用set接下来的思路就是计算每个作为连续序列的开始元素的连续最长序列长度,连续序列的开始元素怎么定义?如果这个不存在这个元素-1,那么这个元素就作为一个连续序列的...原创 2020-04-06 12:33:46 · 162 阅读 · 0 评论 -
leetcode 594. 最长和谐子序列 简单 哈希表
题目:分析:可以看到题目示例并不要求子序列是连续的,其实是降低了难度,只要能统计出个数即可,说到统计个数自然而然地会联想起hashmap,使用hashmap还可以方便知道有没有相差是1的元素代码:class Solution { public int findLHS(int[] nums) { Map<Integer, Integer> map = ne...原创 2020-04-06 11:40:12 · 149 阅读 · 0 评论 -
二叉树的前序,后序遍历,中序遍历(非递归) Java
二叉树的三种遍历如果用递归写都很简单,代码几乎都没有变化前序遍历非递归的前序遍历思路如下:前序遍历:root -> left -> right用栈保存左右节点每次先取出栈顶元素(root),加入结果再把栈顶元素的左右节点加入栈要想用栈实现先遍历左子树再遍历右子树,那么添加到栈的时候就要反过来添加,先添加右子树再添加左子树返回结果/** * Definition fo...原创 2020-03-29 21:28:09 · 138 阅读 · 0 评论 -
leetcode 101. 对称二叉树 简单 树
题目:分析:先理解好镜像的概念再去思考怎么做题。这道题还是比较容易想到用递归的,比较两棵树,剩下的就是思考递归怎么结束有几个条件,1.两棵子树都是空的,2.有一棵子树是空的,3.两个树节点的值不相等代码:/** * Definition for a binary tree node. * public class TreeNode { * int val; * T...原创 2020-03-29 19:54:27 · 119 阅读 · 0 评论