merge PRs

This commit is contained in:
yqq 2021-06-14 16:36:47 +08:00
commit 408d01dc4b
189 changed files with 12163 additions and 2148 deletions

View File

@ -3,7 +3,8 @@
> 1. **介绍**:本项目是一套完整的刷题计划,旨在帮助大家少走弯路,循序渐进学算法,[关注作者](#关于作者) > 1. **介绍**:本项目是一套完整的刷题计划,旨在帮助大家少走弯路,循序渐进学算法,[关注作者](#关于作者)
> 2. **PDF版本** [「代码随想录」算法精讲 PDF 版本](https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ) 。 > 2. **PDF版本** [「代码随想录」算法精讲 PDF 版本](https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ) 。
> 3. **学习社区** : 一起学习打卡/面试技巧/如何选择offer/大厂内推/职场规则/简历修改/技术分享/程序人生。欢迎加入[「代码随想录」学习社区](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ) 。 > 3. **学习社区** : 一起学习打卡/面试技巧/如何选择offer/大厂内推/职场规则/简历修改/技术分享/程序人生。欢迎加入[「代码随想录」学习社区](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ) 。
> 4. **转载须知** :以下所有文章皆为我([程序员Carl](https://github.com/youngyangyang04))的原创。引用本项目文章请注明出处,发现恶意抄袭或搬运,会动用法律武器维护自己的权益。让我们一起维护一个良好的技术创作环境! > 4. **提交代码**本项目统一使用C++语言进行讲解但已经有Java、Python、Go、JavaScript等等多语言版本感谢[这里的每一位贡献者](https://github.com/youngyangyang04/leetcode-master/graphs/contributors),如果你也想贡献代码点亮你的头像,[点击这里](https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A)了解提交代码的方式。
> 5. **转载须知** :以下所有文章皆为我([程序员Carl](https://github.com/youngyangyang04))的原创。引用本项目文章请注明出处,发现恶意抄袭或搬运,会动用法律武器维护自己的权益。让我们一起维护一个良好的技术创作环境!
<p align="center"> <p align="center">
<a href="https://github.com/youngyangyang04/leetcode-master" target="_blank"> <a href="https://github.com/youngyangyang04/leetcode-master" target="_blank">
@ -11,11 +12,16 @@
</a> </a>
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ" target="_blank">
<img src="./pics/知识星球.png" width="600"/>
</a>
# LeetCode 刷题攻略 # LeetCode 刷题攻略
@ -111,14 +117,24 @@
(持续更新中..... (持续更新中.....
## 备战秋招
1. [选择方向的时候,我也迷茫了](https://mp.weixin.qq.com/s/ZCzFiAHZHLqHPLJQXNm75g)
2. [刷题就用库函数了,怎么了?](https://mp.weixin.qq.com/s/6K3_OSaudnHGq2Ey8vqYfg)
3. [关于实习,大家可能有点迷茫!](https://mp.weixin.qq.com/s/xcxzi7c78kQGjvZ8hh7taA)
4. [马上秋招了,慌得很!](https://mp.weixin.qq.com/s/7q7W8Cb2-a5U5atZdOnOFA)
5. [Carl看了上百份简历总结了这些](https://mp.weixin.qq.com/s/sJa87MZD28piCOVMFkIbwQ)
6. [面试中遇到了发散性问题.....](https://mp.weixin.qq.com/s/SSonDxi2pjkSVwHNzZswng)
## 数组 ## 数组
1. [数组过于简单,但你该了解这些!](./problems/数组理论基础.md) 1. [数组过于简单,但你该了解这些!](./problems/数组理论基础.md)
2. [数组:每次遇到二分法,都是一看就会,一写就废](./problems/0704.二分查找.md) 2. [数组:每次遇到二分法,都是一看就会,一写就废](./problems/0704.二分查找.md)
3. [数组:就移除个元素很难么?](./problems/0027.移除元素.md) 3. [数组:就移除个元素很难么?](./problems/0027.移除元素.md)
4. [数组:滑动窗口拯救了你](./problems/0209.长度最小的子数组.md) 4. [数组:有序数组的平方,还有序么?](./problems/0977.有序数组的平方.md)
5. [数组:这个循环可以转懵很多人!](./problems/0059.螺旋矩阵II.md) 5. [数组:滑动窗口拯救了你](./problems/0209.长度最小的子数组.md)
6. [数组:总结篇](./problems/数组总结篇.md) 6. [数组:这个循环可以转懵很多人!](./problems/0059.螺旋矩阵II.md)
7. [数组:总结篇](./problems/数组总结篇.md)
## 链表 ## 链表
@ -169,10 +185,9 @@
6. [链表:删除链表的倒数第 N 个结点](./problems/0019.删除链表的倒数第N个节点.md) 6. [链表:删除链表的倒数第 N 个结点](./problems/0019.删除链表的倒数第N个节点.md)
7. [链表:链表相交](./problems/面试题02.07.链表相交.md) 7. [链表:链表相交](./problems/面试题02.07.链表相交.md)
8. [链表:环找到了,那入口呢?](./problems/0142.环形链表II.md) 8. [链表:环找到了,那入口呢?](./problems/0142.环形链表II.md)
9. [链表:删除链表的倒数第 N 个结点](./problems/0019.删除链表的倒数第N个节点.md) 9. [哈希表:解决了两数之和,那么能解决三数之和么?](./problems/0015.三数之和.md)
10. [哈希表:解决了两数之和,那么能解决三数之和么?](./problems/0015.三数之和.md) 10. [双指针法:一样的道理,能解决四数之和](./problems/0018.四数之和.md)
11. [双指针法:一样的道理,能解决四数之和](./problems/0018.四数之和.md) 11. [双指针法:总结篇!](./problems/双指针总结.md)
12. [双指针法:总结篇!](./problems/双指针总结.md)
## 栈与队列 ## 栈与队列
@ -292,6 +307,7 @@
动态规划专题已经开始啦,来不及解释了,小伙伴们上车别掉队! 动态规划专题已经开始啦,来不及解释了,小伙伴们上车别掉队!
<img src='https://code-thinking.cdn.bcebos.com/pics/动态规划-总结大纲1.jpg' width=500> </img></div>
1. [关于动态规划,你该了解这些!](./problems/动态规划理论基础.md) 1. [关于动态规划,你该了解这些!](./problems/动态规划理论基础.md)
2. [动态规划:斐波那契数](./problems/0509.斐波那契数.md) 2. [动态规划:斐波那契数](./problems/0509.斐波那契数.md)
3. [动态规划:爬楼梯](./problems/0070.爬楼梯.md) 3. [动态规划:爬楼梯](./problems/0070.爬楼梯.md)
@ -305,7 +321,8 @@
背包问题系列: 背包问题系列:
<img src='https://img-blog.csdnimg.cn/202102261550480.png' width=500 alt='背包问题大纲'> </img></div> <img src='https://code-thinking.cdn.bcebos.com/pics/动态规划-背包问题总结.png' width=500 alt='背包问题大纲'> </img></div>
11. [动态规划关于01背包问题你该了解这些](./problems/背包理论基础01背包-1.md) 11. [动态规划关于01背包问题你该了解这些](./problems/背包理论基础01背包-1.md)
12. [动态规划关于01背包问题你该了解这些滚动数组](./problems/背包理论基础01背包-2.md) 12. [动态规划关于01背包问题你该了解这些滚动数组](./problems/背包理论基础01背包-2.md)
@ -334,7 +351,8 @@
股票系列: 股票系列:
<img src='https://code-thinking.cdn.bcebos.com/pics/%E8%82%A1%E7%A5%A8%E9%97%AE%E9%A2%98%E6%80%BB%E7%BB%93.jpg' width=500 alt='股票问题总结'> </img></div> <img src='https://code-thinking.cdn.bcebos.com/pics/股票问题总结.jpg' width=500 alt='股票问题总结'> </img></div>
32. [动态规划:买卖股票的最佳时机](./problems/0121.买卖股票的最佳时机.md) 32. [动态规划:买卖股票的最佳时机](./problems/0121.买卖股票的最佳时机.md)
33. [动态规划:本周我们都讲了这些(系列六)](./problems/周总结/20210225动规周末总结.md) 33. [动态规划:本周我们都讲了这些(系列六)](./problems/周总结/20210225动规周末总结.md)
@ -348,6 +366,9 @@
子序列系列: 子序列系列:
<img src='https://code-thinking.cdn.bcebos.com/pics/动态规划-子序列问题总结.jpg' width=500 alt=''> </img></div>
40. [动态规划:最长递增子序列](./problems/0300.最长上升子序列.md) 40. [动态规划:最长递增子序列](./problems/0300.最长上升子序列.md)
41. [动态规划:最长连续递增序列](./problems/0674.最长连续递增序列.md) 41. [动态规划:最长连续递增序列](./problems/0674.最长连续递增序列.md)
42. [动态规划:最长重复子数组](./problems/0718.最长重复子数组.md) 42. [动态规划:最长重复子数组](./problems/0718.最长重复子数组.md)
@ -361,10 +382,14 @@
52. [为了绝杀编辑距离Carl做了三步铺垫你都知道么](./problems/为了绝杀编辑距离,卡尔做了三步铺垫.md) 52. [为了绝杀编辑距离Carl做了三步铺垫你都知道么](./problems/为了绝杀编辑距离,卡尔做了三步铺垫.md)
53. [动态规划:回文子串](./problems/0647.回文子串.md) 53. [动态规划:回文子串](./problems/0647.回文子串.md)
54. [动态规划:最长回文子序列](./problems/0516.最长回文子序列.md) 54. [动态规划:最长回文子序列](./problems/0516.最长回文子序列.md)
55. [动态规划总结篇](./problems/动态规划总结篇.md)
(持续更新中.... (持续更新中....
## 单调栈
1. [每日温度](./problems/0739.每日温度.md)
## 图论 ## 图论
## 十大排序 ## 十大排序
@ -385,12 +410,7 @@
[各类基础算法模板](https://github.com/youngyangyang04/leetcode/blob/master/problems/算法模板.md) [各类基础算法模板](https://github.com/youngyangyang04/leetcode/blob/master/problems/算法模板.md)
# 备战秋招
1. [技术比较弱,也对技术不感兴趣,如何选择方向?](https://mp.weixin.qq.com/s/ZCzFiAHZHLqHPLJQXNm75g)
2. [刷题就用库函数了,怎么了?](https://mp.weixin.qq.com/s/6K3_OSaudnHGq2Ey8vqYfg)
3. [关于实习,大家可能有点迷茫!](https://mp.weixin.qq.com/s/xcxzi7c78kQGjvZ8hh7taA)
4. [马上秋招了,慌得很!](https://mp.weixin.qq.com/s/7q7W8Cb2-a5U5atZdOnOFA)
# B站算法视频讲解 # B站算法视频讲解
@ -409,6 +429,10 @@
(持续更新中.... (持续更新中....
# 贡献者
你可以[点此链接](https://github.com/youngyangyang04/leetcode-master/graphs/contributors)查看LeetCode-Master的所有贡献者。感谢你们补充了LeetCode-Master的其他语言版本让更多的读者收益于此项目。
# 关于作者 # 关于作者
大家好我是程序员Carl哈工大师兄ACM 校赛、黑龙江省赛、东北四省赛金牌、亚洲区域赛铜牌获得者先后在腾讯和百度从事后端技术研发CSDN博客专家。对算法和C++后端技术有一定的见解利用工作之余重新刷leetcode。 大家好我是程序员Carl哈工大师兄ACM 校赛、黑龙江省赛、东北四省赛金牌、亚洲区域赛铜牌获得者先后在腾讯和百度从事后端技术研发CSDN博客专家。对算法和C++后端技术有一定的见解利用工作之余重新刷leetcode。
@ -420,7 +444,7 @@
<a name="微信"></a> <a name="微信"></a>
<img src="https://img-blog.csdnimg.cn/20200814140330894.png" data-img="1" width="175" height="175"> <img src="https://img-blog.csdnimg.cn/20200814140330894.png" data-img="1" width="175" height="175">
# 我的公众号 # 公众号
更多精彩文章持续更新微信搜索「代码随想录」第一时间围观关注后回复「666」可以获得所有算法专题原创PDF。 更多精彩文章持续更新微信搜索「代码随想录」第一时间围观关注后回复「666」可以获得所有算法专题原创PDF。

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 1. 两数之和 ## 1. 两数之和
@ -29,10 +29,10 @@ https://leetcode-cn.com/problems/two-sum/
很明显暴力的解法是两层for循环查找时间复杂度是O(n^2)。 很明显暴力的解法是两层for循环查找时间复杂度是O(n^2)。
建议大家做这道题目之前,先做一下这两道 建议大家做这道题目之前,先做一下这两道
* [242. 有效的字母异位词](https://mp.weixin.qq.com/s/vM6OszkM6L1Mx2Ralm9Dig) * [242. 有效的字母异位词](https://mp.weixin.qq.com/s/ffS8jaVFNUWyfn_8T31IdA)
* [349. 两个数组的交集](https://mp.weixin.qq.com/s/N9iqAchXreSVW7zXUS4BVA) * [349. 两个数组的交集](https://mp.weixin.qq.com/s/aMSA5zrp3jJcLjuSB0Es2Q)
[242. 有效的字母异位词](https://mp.weixin.qq.com/s/vM6OszkM6L1Mx2Ralm9Dig) 这道题目是用数组作为哈希表来解决哈希问题,[349. 两个数组的交集](https://mp.weixin.qq.com/s/N9iqAchXreSVW7zXUS4BVA)这道题目是通过set作为哈希表来解决哈希问题。 [242. 有效的字母异位词](https://mp.weixin.qq.com/s/ffS8jaVFNUWyfn_8T31IdA) 这道题目是用数组作为哈希表来解决哈希问题,[349. 两个数组的交集](https://mp.weixin.qq.com/s/aMSA5zrp3jJcLjuSB0Es2Q)这道题目是通过set作为哈希表来解决哈希问题。
本题呢则要使用map那么来看一下使用数组和set来做哈希法的局限。 本题呢则要使用map那么来看一下使用数组和set来做哈希法的局限。
@ -51,13 +51,14 @@ C++中map有三种类型
std::unordered_map 底层实现为哈希表std::map 和std::multimap 的底层实现是红黑树。 std::unordered_map 底层实现为哈希表std::map 和std::multimap 的底层实现是红黑树。
同理std::map 和std::multimap 的key也是有序的这个问题也经常作为面试题考察对语言容器底层的理解。 更多哈希表的理论知识请看[关于哈希表,你该了解这些!](https://mp.weixin.qq.com/s/g8N6WmoQmsCUw3_BaWxHZA)。 同理std::map 和std::multimap 的key也是有序的这个问题也经常作为面试题考察对语言容器底层的理解。 更多哈希表的理论知识请看[关于哈希表,你该了解这些!](https://mp.weixin.qq.com/s/RSUANESA_tkhKhYe3ZR8Jg)。
**这道题目中并不需要key有序选择std::unordered_map 效率更高!** **这道题目中并不需要key有序选择std::unordered_map 效率更高!**
解题思路动画如下: 解题思路动画如下:
<video src='https://code-thinking.cdn.bcebos.com/gifs/1.%E4%B8%A4%E6%95%B0%E4%B9%8B%E5%92%8C.mp4' controls='controls' width='640' height='320' autoplay='autoplay'> Your browser does not support the video tag.</video></div> ![](https://code-thinking.cdn.bcebos.com/gifs/1.两数之和.gif)
C++代码: C++代码:
@ -134,6 +135,21 @@ func twoSum(nums []int, target int) []int {
} }
``` ```
```go
// 使用map方式解题降低时间复杂度
func twoSum(nums []int, target int) []int {
m := make(map[int]int)
for index, val := range nums {
if preIndex, ok := m[target-val]; ok {
return []int{preIndex, index}
} else {
m[val] = index
}
}
return []int{}
}
```
Rust Rust
```rust ```rust
@ -156,6 +172,21 @@ impl Solution {
} }
``` ```
Javascript
```javascript
var twoSum = function (nums, target) {
let hash = {};
for (let i = 0; i < nums.length; i++) {
if (hash[target - nums[i]] !== undefined) {
return [i, hash[target - nums[i]]];
}
hash[nums[i]] = i;
}
return [];
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -105,8 +105,7 @@ public:
时间复杂度O(n^2)。 时间复杂度O(n^2)。
C++代码代码如下:
## 双指针法C++代码
```C++ ```C++
class Solution { class Solution {
@ -163,13 +162,14 @@ public:
# 思考题 # 思考题
既然三数之和可以使用双指针法,我们之前讲过的[两数之和](https://mp.weixin.qq.com/s/uVAtjOHSeqymV8FeQbliJQ),可不可以使用双指针法呢?
既然三数之和可以使用双指针法,我们之前讲过的[1.两数之和](https://mp.weixin.qq.com/s/vaMsLnH-f7_9nEK4Cuu3KQ),可不可以使用双指针法呢?
如果不能,题意如何更改就可以使用双指针法呢? **大家留言说出自己的想法吧!** 如果不能,题意如何更改就可以使用双指针法呢? **大家留言说出自己的想法吧!**
两数之和 就不能使用双指针法,因为[两数之和](https://mp.weixin.qq.com/s/uVAtjOHSeqymV8FeQbliJQ)要求返回的是索引下表, 而双指针法一定要排序,一旦排序之后原数组的索引就被改变了。 两数之和 就不能使用双指针法,因为[1.两数之和](https://mp.weixin.qq.com/s/vaMsLnH-f7_9nEK4Cuu3KQ)要求返回的是索引下表, 而双指针法一定要排序,一旦排序之后原数组的索引就被改变了。
如果[两数之和](https://mp.weixin.qq.com/s/uVAtjOHSeqymV8FeQbliJQ)要求返回的是数值的话,就可以使用双指针法了。 如果[1.两数之和](https://mp.weixin.qq.com/s/vaMsLnH-f7_9nEK4Cuu3KQ)要求返回的是数值的话,就可以使用双指针法了。
@ -218,8 +218,33 @@ class Solution {
``` ```
Python Python
```Python
class Solution:
def threeSum(self, nums):
ans = []
n = len(nums)
nums.sort()
for i in range(n):
left = i + 1
right = n - 1
if nums[i] > 0:
break
if i >= 1 and nums[i] == nums[i - 1]:
continue
while left < right:
total = nums[i] + nums[left] + nums[right]
if total > 0:
right -= 1
elif total < 0:
left += 1
else:
ans.append([nums[i], nums[left], nums[right]])
while left != right and nums[left] == nums[left + 1]: left += 1
while left != right and nums[right] == nums[right - 1]: right -= 1
left += 1
right -= 1
return ans
```
Go Go
```Go ```Go
func threeSum(nums []int)[][]int{ func threeSum(nums []int)[][]int{
@ -256,8 +281,78 @@ func threeSum(nums []int)[][]int{
} }
``` ```
javaScript:
```js
/**
* @param {number[]} nums
* @return {number[][]}
*/
// 循环内不考虑去重
var threeSum = function(nums) {
const len = nums.length;
if(len < 3) return [];
nums.sort((a, b) => a - b);
const resSet = new Set();
for(let i = 0; i < len - 2; i++) {
if(nums[i] > 0) break;
let l = i + 1, r = len - 1;
while(l < r) {
const sum = nums[i] + nums[l] + nums[r];
if(sum < 0) { l++; continue };
if(sum > 0) { r--; continue };
resSet.add(`${nums[i]},${nums[l]},${nums[r]}`);
l++;
r--;
}
}
return Array.from(resSet).map(i => i.split(","));
};
// 去重优化
var threeSum = function(nums) {
const len = nums.length;
if(len < 3) return [];
nums.sort((a, b) => a - b);
const res = [];
for(let i = 0; i < len - 2; i++) {
if(nums[i] > 0) break;
// a去重
if(i > 0 && nums[i] === nums[i - 1]) continue;
let l = i + 1, r = len - 1;
while(l < r) {
const sum = nums[i] + nums[l] + nums[r];
if(sum < 0) { l++; continue };
if(sum > 0) { r--; continue };
res.push([nums[i], nums[l], nums[r]])
// b c 去重
while(l < r && nums[l] === nums[++l]);
while(l < r && nums[r] === nums[--r]);
}
}
return res;
};
```
ruby:
```ruby
def is_valid(strs)
symbol_map = {')' => '(', '}' => '{', ']' => '['}
stack = []
strs.size.times {|i|
c = strs[i]
if symbol_map.has_key?(c)
top_e = stack.shift
return false if symbol_map[c] != top_e
else
stack.unshift(c)
end
}
stack.empty?
end
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 17.电话号码的字母组合 # 17.电话号码的字母组合
@ -137,7 +137,7 @@ for (int i = 0; i < letters.size(); i++) {
关键地方都讲完了,按照[关于回溯算法,你该了解这些!](https://mp.weixin.qq.com/s/gjSgJbNbd1eAA5WkA-HeWw)中的回溯法模板不难写出如下C++代码: 关键地方都讲完了,按照[关于回溯算法,你该了解这些!](https://mp.weixin.qq.com/s/gjSgJbNbd1eAA5WkA-HeWw)中的回溯法模板不难写出如下C++代码:
``` ```c++
// 版本一 // 版本一
class Solution { class Solution {
private: private:
@ -183,7 +183,7 @@ public:
一些写法,是把回溯的过程放在递归函数里了,例如如下代码,我可以写成这样:(注意注释中不一样的地方) 一些写法,是把回溯的过程放在递归函数里了,例如如下代码,我可以写成这样:(注意注释中不一样的地方)
``` ```c++
// 版本二 // 版本二
class Solution { class Solution {
private: private:
@ -272,7 +272,7 @@ class Solution {
String str = numString[digits.charAt(num) - '0']; String str = numString[digits.charAt(num) - '0'];
for (int i = 0; i < str.length(); i++) { for (int i = 0; i < str.length(); i++) {
temp.append(str.charAt(i)); temp.append(str.charAt(i));
//回溯 //c
backTracking(digits, numString, num + 1); backTracking(digits, numString, num + 1);
//剔除末尾的继续尝试 //剔除末尾的继续尝试
temp.deleteCharAt(temp.length() - 1); temp.deleteCharAt(temp.length() - 1);
@ -283,9 +283,92 @@ class Solution {
Python Python
```Python
class Solution:
ans = []
s = ''
letterMap = {
'2': 'abc',
'3': 'def',
'4': 'ghi',
'5': 'jkl',
'6': 'mno',
'7': 'pqrs',
'8': 'tuv',
'9': 'wxyz'
}
def letterCombinations(self, digits):
self.ans.clear()
if digits == '':
return self.ans
self.backtracking(digits, 0)
return self.ans
def backtracking(self, digits, index):
if index == len(digits):
self.ans.append(self.s)
return
else:
letters = self.letterMap[digits[index]] # 取出数字对应的字符集
for letter in letters:
self.s = self.s + letter # 处理
self.backtracking(digits, index + 1)
self.s = self.s[:-1] # 回溯
```
python3
```py
class Solution:
def letterCombinations(self, digits: str) -> List[str]:
self.s = ""
res = []
letterMap = ["","","abc","def","ghi","jkl","mno","pqrs","tuv","wxyz"]
if len(digits) == 0: return res
def backtrack(digits,index):
if index == len(digits):
return res.append(self.s)
digit = int(digits[index]) #将index指向的数字转为int
letters = letterMap[digit] #取数字对应的字符集
for i in range(len(letters)):
self.s += letters[i]
backtrack(digits,index + 1) #递归注意index+1一下层要处理下一个数字
self.s = self.s[:-1] #回溯
backtrack(digits,0)
return res
```
Go Go
javaScript
```js
var letterCombinations = function(digits) {
const k = digits.length;
const map = ["","","abc","def","ghi","jkl","mno","pqrs","tuv","wxyz"];
if(!k) return [];
if(k === 1) return map[digits].split("");
const res = [], path = [];
backtracking(digits, k, 0);
return res;
function backtracking(n, k, a) {
if(path.length === k) {
res.push(path.join(""));
return;
}
for(const v of map[n[a]]) {
path.push(v);
backtracking(n, k, a + 1);
path.pop();
}
}
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 一样的道理,能解决四数之和 > 一样的道理,能解决四数之和
@ -31,38 +31,39 @@ https://leetcode-cn.com/problems/4sum/
# 思路 # 思路
四数之和,和[三数之和](https://mp.weixin.qq.com/s/r5cgZFu0tv4grBAexdcd8A)是一个思路,都是使用双指针法, 基本解法就是在[三数之和](https://mp.weixin.qq.com/s/r5cgZFu0tv4grBAexdcd8A) 的基础上再套一层for循环。 四数之和,和[15.三数之和](https://mp.weixin.qq.com/s/QfTNEByq1YlNSXRKEumwHg)是一个思路,都是使用双指针法, 基本解法就是在[15.三数之和](https://mp.weixin.qq.com/s/QfTNEByq1YlNSXRKEumwHg) 的基础上再套一层for循环。
但是有一些细节需要注意,例如: 不要判断`nums[k] > target` 就返回了,三数之和 可以通过 `nums[i] > 0` 就返回了,因为 0 已经是确定的数了,四数之和这道题目 target是任意值。大家亲自写代码就能感受出来 但是有一些细节需要注意,例如: 不要判断`nums[k] > target` 就返回了,三数之和 可以通过 `nums[i] > 0` 就返回了,因为 0 已经是确定的数了,四数之和这道题目 target是任意值。大家亲自写代码就能感受出来
[三数之和](https://mp.weixin.qq.com/s/r5cgZFu0tv4grBAexdcd8A)的双指针解法是一层for循环num[i]为确定值然后循环内有left和right下表作为双指针找到nums[i] + nums[left] + nums[right] == 0。 [15.三数之和](https://mp.weixin.qq.com/s/QfTNEByq1YlNSXRKEumwHg)的双指针解法是一层for循环num[i]为确定值然后循环内有left和right下表作为双指针找到nums[i] + nums[left] + nums[right] == 0。
四数之和的双指针解法是两层for循环nums[k] + nums[i]为确定值依然是循环内有left和right下表作为双指针找出nums[k] + nums[i] + nums[left] + nums[right] == target的情况三数之和的时间复杂度是O(n^2)四数之和的时间复杂度是O(n^3) 。 四数之和的双指针解法是两层for循环nums[k] + nums[i]为确定值依然是循环内有left和right下表作为双指针找出nums[k] + nums[i] + nums[left] + nums[right] == target的情况三数之和的时间复杂度是O(n^2)四数之和的时间复杂度是O(n^3) 。
那么一样的道理,五数之和、六数之和等等都采用这种解法。 那么一样的道理,五数之和、六数之和等等都采用这种解法。
对于[三数之和](https://mp.weixin.qq.com/s/r5cgZFu0tv4grBAexdcd8A)双指针法就是将原本暴力O(n^3)的解法降为O(n^2)的解法四数之和的双指针解法就是将原本暴力O(n^4)的解法降为O(n^3)的解法。 对于[15.三数之和](https://mp.weixin.qq.com/s/QfTNEByq1YlNSXRKEumwHg)双指针法就是将原本暴力O(n^3)的解法降为O(n^2)的解法四数之和的双指针解法就是将原本暴力O(n^4)的解法降为O(n^3)的解法。
之前我们讲过哈希表的经典题目:[四数相加II](https://mp.weixin.qq.com/s/Ue8pKKU5hw_m-jPgwlHcbA)相对于本题简单很多因为本题是要求在一个集合中找出四个数相加等于target同时四元组不能重复。 之前我们讲过哈希表的经典题目:[454.四数相加II](https://mp.weixin.qq.com/s/12g_w6RzHuEpFts1pT6BWw)相对于本题简单很多因为本题是要求在一个集合中找出四个数相加等于target同时四元组不能重复。
而[四数相加II](https://mp.weixin.qq.com/s/Ue8pKKU5hw_m-jPgwlHcbA)是四个独立的数组只要找到A[i] + B[j] + C[k] + D[l] = 0就可以不用考虑有重复的四个元素相加等于0的情况所以相对于本题还是简单了不少 而[454.四数相加II](https://mp.weixin.qq.com/s/12g_w6RzHuEpFts1pT6BWw)是四个独立的数组只要找到A[i] + B[j] + C[k] + D[l] = 0就可以不用考虑有重复的四个元素相加等于0的情况所以相对于本题还是简单了不少
我们来回顾一下,几道题目使用了双指针法。 我们来回顾一下,几道题目使用了双指针法。
双指针法将时间复杂度O(n^2)的解法优化为 O(n)的解法。也就是降一个数量级,题目如下: 双指针法将时间复杂度O(n^2)的解法优化为 O(n)的解法。也就是降一个数量级,题目如下:
* [0027.移除元素](https://mp.weixin.qq.com/s/wj0T-Xs88_FHJFwayElQlA)
* [15.三数之和](https://mp.weixin.qq.com/s/r5cgZFu0tv4grBAexdcd8A) * [27.移除元素](https://mp.weixin.qq.com/s/RMkulE4NIb6XsSX83ra-Ww)
* [15.三数之和](https://mp.weixin.qq.com/s/QfTNEByq1YlNSXRKEumwHg)
* [18.四数之和](https://mp.weixin.qq.com/s/nQrcco8AZJV1pAOVjeIU_g) * [18.四数之和](https://mp.weixin.qq.com/s/nQrcco8AZJV1pAOVjeIU_g)
双指针来记录前后指针实现链表反转:
* [206.反转链表](https://mp.weixin.qq.com/s/pnvVP-0ZM7epB8y3w_Njwg) 操作链表:
使用双指针来确定有环: * [206.反转链表](https://mp.weixin.qq.com/s/ckEvIVGcNLfrz6OLOMoT0A)
* [19.删除链表的倒数第N个节点](https://mp.weixin.qq.com/s/gxu65X1343xW_sBrkTz0Eg)
* [面试题 02.07. 链表相交](https://mp.weixin.qq.com/s/BhfFfaGvt9Zs7UmH4YehZw)
* [142题.环形链表II](https://mp.weixin.qq.com/s/gt_VH3hQTqNxyWcl1ECSbQ)
* [142题.环形链表II](https://mp.weixin.qq.com/s/_QVP3IkRZWx9zIpQRgajzA) 双指针法在字符串题目中还有很多应用,后面还会介绍到。
双指针法在数组和链表中还有很多应用,后面还会介绍到。
C++代码 C++代码
@ -165,11 +166,75 @@ class Solution {
``` ```
Python Python
```python
class Solution(object):
def fourSum(self, nums, target):
"""
:type nums: List[int]
:type target: int
:rtype: List[List[int]]
"""
# use a dict to store value:showtimes
hashmap = dict()
for n in nums:
if n in hashmap:
hashmap[n] += 1
else:
hashmap[n] = 1
# good thing about using python is you can use set to drop duplicates.
ans = set()
for i in range(len(nums)):
for j in range(i + 1, len(nums)):
for k in range(j + 1, len(nums)):
val = target - (nums[i] + nums[j] + nums[k])
if val in hashmap:
# make sure no duplicates.
count = (nums[i] == val) + (nums[j] == val) + (nums[k] == val)
if hashmap[val] > count:
ans.add(tuple(sorted([nums[i], nums[j], nums[k], val])))
else:
continue
return ans
```
Go Go
javaScript:
```js
/**
* @param {number[]} nums
* @param {number} target
* @return {number[][]}
*/
var fourSum = function(nums, target) {
const len = nums.length;
if(len < 4) return [];
nums.sort((a, b) => a - b);
const res = [];
for(let i = 0; i < len - 3; i++) {
// 去重i
if(i > 0 && nums[i] === nums[i - 1]) continue;
for(let j = i + 1; j < len - 2; j++) {
// 去重j
if(j > i + 1 && nums[j] === nums[j - 1]) continue;
let l = j + 1, r = len - 1;
while(l < r) {
const sum = nums[i] + nums[j] + nums[l] + nums[r];
if(sum < target) { l++; continue}
if(sum > target) { r--; continue}
res.push([nums[i], nums[j], nums[l], nums[r]]);
while(l < r && nums[l] === nums[++l]);
while(l < r && nums[r] === nums[--r]);
}
}
}
return res;
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -112,29 +112,79 @@ class Solution {
} }
} }
``` ```
Python:
```python
# Definition for singly-linked list.
# class ListNode:
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution:
def removeNthFromEnd(self, head: ListNode, n: int) -> ListNode:
head_dummy = ListNode()
head_dummy.next = head
slow, fast = head_dummy, head_dummy
while(n!=0): #fast先往前走n步
fast = fast.next
n -= 1
while(fast.next!=None):
slow = slow.next
fast = fast.next
#fast 走到结尾后slow的下一个节点为倒数第N个节点
slow.next = slow.next.next #删除
return head_dummy.next
```
Go: Go:
```Go ```Go
/**
* Definition for singly-linked list.
* type ListNode struct {
* Val int
* Next *ListNode
* }
*/
func removeNthFromEnd(head *ListNode, n int) *ListNode { func removeNthFromEnd(head *ListNode, n int) *ListNode {
result:=&ListNode{} dummyHead := &ListNode{}
result.Next=head dummyHead.Next = head
var pre *ListNode cur := head
cur:=result prev := dummyHead
i := 1 i := 1
for head!=nil{ for cur != nil {
if i>=n{
pre=cur
cur = cur.Next cur = cur.Next
if i > n {
prev = prev.Next
} }
head=head.Next
i++ i++
} }
pre.Next=pre.Next.Next prev.Next = prev.Next.Next
return result.Next return dummyHead.Next
} }
``` ```
JavaScript:
```js
/**
* @param {ListNode} head
* @param {number} n
* @return {ListNode}
*/
var removeNthFromEnd = function(head, n) {
let ret = new ListNode(0, head),
slow = fast = ret;
while(n--) fast = fast.next;
if(!fast) return ret.next;
while (fast.next) {
fast = fast.next;
slow = slow.next
};
slow.next = slow.next.next;
return ret.next;
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)
* B站视频[代码随想录](https://space.bilibili.com/525438321) * B站视频[代码随想录](https://space.bilibili.com/525438321)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -162,6 +162,33 @@ class Solution {
return deque.isEmpty(); return deque.isEmpty();
} }
} }
// 方法2
class Solution {
public boolean isValid(String s) {
Stack<Character> stack = new Stack<>();
Map<Character, Character> map = new HashMap<Character, Character>() {
{
put('}', '{');
put(']', '[');
put(')', '(');
}
};
for (Character c : s.toCharArray()) { // 顺序读取字符
if (!stack.isEmpty() && map.containsKey(c)) { // 是右括号 && 栈不为空
if (stack.peek() == map.get(c)) { // 取其对应的左括号直接和栈顶比
stack.pop(); // 相同则抵消,出栈
} else {
return false; // 不同则直接返回
}
} else {
stack.push(c); // 左括号,直接入栈
}
}
return stack.isEmpty(); // 看左右是否抵消完
}
}
``` ```
Python Python
@ -220,6 +247,49 @@ def is_valid(strs)
end end
``` ```
Javascript:
```javascript
var isValid = function (s) {
const stack = [];
for (let i = 0; i < s.length; i++) {
let c = s[i];
switch (c) {
case '(':
stack.push(')');
break;
case '[':
stack.push(']');
break;
case '{':
stack.push('}');
break;
default:
if (c !== stack.pop()) {
return false;
}
}
}
return stack.length === 0;
};
// 简化版本
var isValid = function(s) {
const stack = [],
map = {
"(":")",
"{":"}",
"[":"]"
};
for(const x of s) {
if(x in map) {
stack.push(x);
continue;
};
if(map[stack.pop()] !== x) return false;
}
return !stack.length;
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,11 +1,11 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 24. 两两交换链表中的节点 ## 24. 两两交换链表中的节点
@ -87,10 +87,116 @@ public:
Java Java
```Java
// 递归版本
class Solution {
public ListNode swapPairs(ListNode head) {
// base case 退出提交
if(head == null || head.next == null) return head;
// 获取当前节点的下一个节点
ListNode next = head.next;
// 进行递归
ListNode newNode = swapPairs(next.next);
// 这里进行交换
next.next = head;
head.next = newNode;
return next;
}
}
```
```java
// 虚拟头结点
class Solution {
public ListNode swapPairs(ListNode head) {
ListNode dummyNode = new ListNode(0);
dummyNode.next = head;
ListNode prev = dummyNode;
while (prev.next != null && prev.next.next != null) {
ListNode temp = head.next.next; // 缓存 next
prev.next = head.next; // 将 prev 的 next 改为 head 的 next
head.next.next = head; // 将 head.next(prev.next) 的next指向 head
head.next = temp; // 将head 的 next 接上缓存的temp
prev = head; // 步进1位
head = head.next; // 步进1位
}
return dummyNode.next;
}
}
```
Python Python
```python
class Solution:
def swapPairs(self, head: ListNode) -> ListNode:
dummy = ListNode(0) #设置一个虚拟头结点
dummy.next = head
cur = dummy
while cur.next and cur.next.next:
tmp = cur.next #记录临时节点
tmp1 = cur.next.next.next #记录临时节点
cur.next = cur.next.next #步骤一
cur.next.next = tmp #步骤二
cur.next.next.next = tmp1 #步骤三
cur = cur.next.next #cur移动两位,准备下一轮交换
return dummy.next
```
Go Go
```go
func swapPairs(head *ListNode) *ListNode {
dummy := &ListNode{
Next: head,
}
//head=list[i]
//pre=list[i-1]
pre := dummy
for head != nil && head.Next != nil {
pre.Next = head.Next
next := head.Next.Next
head.Next.Next = head
head.Next = next
//pre=list[(i+2)-1]
pre = head
//head=list[(i+2)]
head = next
}
return dummy.Next
}
```
```go
// 递归版本
func swapPairs(head *ListNode) *ListNode {
if head == nil || head.Next == nil {
return head
}
next := head.Next
head.Next = swapPairs(next.Next)
next.Next = head
return next
}
```
Javascript:
```javascript
var swapPairs = function (head) {
let ret = new ListNode(0, head), temp = ret;
while (temp.next && temp.next.next) {
let cur = temp.next.next, pre = temp.next;
pre.next = cur.next;
cur.next = pre;
temp.next = cur;
temp = pre;
}
return ret.next;
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 27. 移除元素 ## 27. 移除元素
@ -186,6 +186,36 @@ var removeElement = (nums, val) => {
}; };
``` ```
Ruby:
```ruby
def remove_element(nums, val)
i = 0
nums.each_index do |j|
if nums[j] != val
nums[i] = nums[j]
i+=1
end
end
i
end
```
Rust:
```rust
pub fn remove_element(nums: &mut Vec<i32>, val: i32) -> &mut Vec<i32> {
let mut start: usize = 0;
while start < nums.len() {
if nums[start] == val {
nums.remove(start);
}
start += 1;
}
nums
}
fn main() {
let mut nums = vec![5,1,3,5,2,3,4,1];
println!("{:?}",remove_element(&mut nums, 5));
}
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)
* B站视频[代码随想录](https://space.bilibili.com/525438321) * B站视频[代码随想录](https://space.bilibili.com/525438321)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 在一个串中查找是否出现过另一个串这是KMP的看家本领。 > 在一个串中查找是否出现过另一个串这是KMP的看家本领。
@ -61,11 +61,6 @@ KMP的经典思想就是:**当出现字符串不匹配时,可以记录一部
读完本篇可以顺便把leetcode上28.实现strStr()题目做了。 读完本篇可以顺便把leetcode上28.实现strStr()题目做了。
如果文字实在看不下去就看我在B站上的视频吧如下
* [帮你把KMP算法学个通透理论篇B站](https://www.bilibili.com/video/BV1PD4y1o7nd/)
* [帮你把KMP算法学个通透求next数组代码篇B站](https://www.bilibili.com/video/BV1M5411j7Xx/)
# 什么是KMP # 什么是KMP
@ -726,6 +721,94 @@ class Solution:
Go Go
```go
// 方法一:前缀表使用减1实现
// getNext 构造前缀表next
// params:
// next 前缀表数组
// s 模式串
func getNext(next []int, s string) {
j := -1 // j表示 最长相等前后缀长度
next[0] = j
for i := 1; i < len(s); i++ {
for j >= 0 && s[i] != s[j+1] {
j = next[j] // 回退前一位
}
if s[i] == s[j+1] {
j++
}
next[i] = j // next[i]是i包括i之前的最长相等前后缀长度
}
}
func strStr(haystack string, needle string) int {
if len(needle) == 0 {
return 0
}
next := make([]int, len(needle))
getNext(next, needle)
j := -1 // 模式串的起始位置 next为-1 因此也为-1
for i := 0; i < len(haystack); i++ {
for j >= 0 && haystack[i] != needle[j+1] {
j = next[j] // 寻找下一个匹配点
}
if haystack[i] == needle[j+1] {
j++
}
if j == len(needle)-1 { // j指向了模式串的末尾
return i - len(needle) + 1
}
}
return -1
}
```
```go
// 方法二: 前缀表无减一或者右移
// getNext 构造前缀表next
// params:
// next 前缀表数组
// s 模式串
func getNext(next []int, s string) {
j := 0
next[0] = j
for i := 1; i < len(s); i++ {
for j > 0 && s[i] != s[j] {
j = next[j-1]
}
if s[i] == s[j] {
j++
}
next[i] = j
}
}
func strStr(haystack string, needle string) int {
n := len(needle)
if n == 0 {
return 0
}
j := 0
next := make([]int, n)
getNext(next, needle)
for i := 0; i < len(haystack); i++ {
for j > 0 && haystack[i] != needle[j] {
j = next[j-1] // 回退到j的前一位
}
if haystack[i] == needle[j] {
j++
}
if j == n {
return i - n + 1
}
}
return -1
}
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -116,7 +116,7 @@ public:
**大家要仔细看注释思考为什么要写while(left <= right) 为什么要写right = middle - 1**。 **大家要仔细看注释思考为什么要写while(left <= right) 为什么要写right = middle - 1**。
``` ```C++
class Solution { class Solution {
public: public:
int searchInsert(vector<int>& nums, int target) { int searchInsert(vector<int>& nums, int target) {
@ -257,7 +257,25 @@ class Solution:
Go Go
JavaScript:
```js
var searchInsert = function (nums, target) {
let l = 0, r = nums.length - 1, ans = nums.length;
while (l <= r) {
const mid = l + Math.floor((r - l) >> 1);
if (target > nums[mid]) {
l = mid + 1;
} else {
ans = mid;
r = mid - 1;
}
}
return ans;
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
如果对回溯法理论还不清楚的同学,可以先看这个视频[视频来了!!带你学透回溯算法(理论篇)](https://mp.weixin.qq.com/s/wDd5azGIYWjbU0fdua_qBg) 如果对回溯法理论还不清楚的同学,可以先看这个视频[视频来了!!带你学透回溯算法(理论篇)](https://mp.weixin.qq.com/s/wDd5azGIYWjbU0fdua_qBg)
@ -287,11 +287,97 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def solveSudoku(self, board: List[List[str]]) -> None:
"""
Do not return anything, modify board in-place instead.
"""
def backtrack(board):
for i in range(len(board)): #遍历行
for j in range(len(board[0])): #遍历列
if board[i][j] != ".": continue
for k in range(1,10): #(i, j) 这个位置放k是否合适
if isValid(i,j,k,board):
board[i][j] = str(k) #放置k
if backtrack(board): return True #如果找到合适一组立刻返回
board[i][j] = "." #回溯撤销k
return False #9个数都试完了都不行那么就返回false
return True #遍历完没有返回false,说明找到了合适棋盘位置了
def isValid(row,col,val,board):
for i in range(9): #判断行里是否重复
if board[row][i] == str(val):
return False
for j in range(9): #判断列里是否重复
if board[j][col] == str(val):
return False
startRow = (row // 3) * 3
startcol = (col // 3) * 3
for i in range(startRow,startRow + 3): #判断9方格里是否重复
for j in range(startcol,startcol + 3):
if board[i][j] == str(val):
return False
return True
backtrack(board)
```
Go Go
Javascript:
```Javascript
var solveSudoku = function(board) {
function isValid(row, col, val, board) {
let len = board.length
// 行不能重复
for(let i = 0; i < len; i++) {
if(board[row][i] === val) {
return false
}
}
// 列不能重复
for(let i = 0; i < len; i++) {
if(board[i][col] === val) {
return false
}
}
let startRow = Math.floor(row / 3) * 3
let startCol = Math.floor(col / 3) * 3
for(let i = startRow; i < startRow + 3; i++) {
for(let j = startCol; j < startCol + 3; j++) {
if(board[i][j] === val) {
return false
}
}
}
return true
}
function backTracking() {
for(let i = 0; i < board.length; i++) {
for(let j = 0; j < board[0].length; j++) {
if(board[i][j] !== '.') continue
for(let val = 1; val <= 9; val++) {
if(isValid(i, j, `${val}`, board)) {
board[i][j] = `${val}`
if (backTracking()) {
return true
}
board[i][j] = `.`
}
}
return false
}
}
return true
}
backTracking(board)
return board
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 39. 组合总和 ## 39. 组合总和
@ -237,45 +237,81 @@ public:
Java Java
```Java ```Java
// 剪枝优化
class Solution { class Solution {
List<List<Integer>> lists = new ArrayList<>(); public List<List<Integer>> combinationSum(int[] candidates, int target) {
Deque<Integer> deque = new LinkedList<>(); List<List<Integer>> res = new ArrayList<>();
Arrays.sort(candidates); // 先进行排序
public List<List<Integer>> combinationSum3(int k, int n) { backtracking(res, new ArrayList<>(), candidates, target, 0, 0);
int[] arr = new int[]{1, 2, 3, 4, 5, 6, 7, 8, 9}; return res;
backTracking(arr, n, k, 0);
return lists;
} }
public void backTracking(int[] arr, int n, int k, int startIndex) { public void backtracking(List<List<Integer>> res, List<Integer> path, int[] candidates, int target, int sum, int idx) {
//如果 n 小于0没必要继续本次递归已经不符合要求了 // 找到了数字和为 target 的组合
if (n < 0) { if (sum == target) {
res.add(new ArrayList<>(path));
return; return;
} }
if (deque.size() == k) {
if (n == 0) { for (int i = idx; i < candidates.length; i++) {
lists.add(new ArrayList(deque)); // 如果 sum + candidates[i] > target 就终止遍历
} if (sum + candidates[i] > target) break;
return; path.add(candidates[i]);
} backtracking(res, path, candidates, target, sum + candidates[i], i);
for (int i = startIndex; i < arr.length - (k - deque.size()) + 1; i++) { path.remove(path.size() - 1); // 回溯,移除路径 path 最后一个元素
deque.push(arr[i]);
//减去当前元素
n -= arr[i];
backTracking(arr, n, k, i + 1);
//恢复n
n += deque.pop();
} }
} }
} }
``` ```
Python Python
```python3
class Solution:
def combinationSum(self, candidates: List[int], target: int) -> List[List[int]]:
res = []
path = []
def backtrack(candidates,target,sum,startIndex):
if sum > target: return
if sum == target: return res.append(path[:])
for i in range(startIndex,len(candidates)):
if sum + candidates[i] >target: return #如果 sum + candidates[i] > target 就终止遍历
sum += candidates[i]
path.append(candidates[i])
backtrack(candidates,target,sum,i) #startIndex = i:表示可以重复读取当前的数
sum -= candidates[i] #回溯
path.pop() #回溯
candidates = sorted(candidates) #需要排序
backtrack(candidates,target,0,0)
return res
```
Go Go
JavaScript
```js
var combinationSum = function(candidates, target) {
const res = [], path = [];
candidates.sort(); // 排序
backtracking(0, 0);
return res;
function backtracking(j, sum) {
if (sum > target) return;
if (sum === target) {
res.push(Array.from(path));
return;
}
for(let i = j; i < candidates.length; i++ ) {
const n = candidates[i];
if(n > target - sum) continue;
path.push(n);
sum += n;
backtracking(i, sum);
path.pop();
sum -= n;
}
}
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 这篇可以说是全网把组合问题如何去重,讲的最清晰的了! > 这篇可以说是全网把组合问题如何去重,讲的最清晰的了!
@ -292,13 +292,61 @@ class Solution {
} }
} }
``` ```
Python Python
```py
class Solution:
def combinationSum2(self, candidates: List[int], target: int) -> List[List[int]]:
res = []
path = []
def backtrack(candidates,target,sum,startIndex):
if sum == target: res.append(path[:])
for i in range(startIndex,len(candidates)): #要对同一树层使用过的元素进行跳过
if sum + candidates[i] > target: return
if i > startIndex and candidates[i] == candidates[i-1]: continue #直接用startIndex来去重,要对同一树层使用过的元素进行跳过
sum += candidates[i]
path.append(candidates[i])
backtrack(candidates,target,sum,i+1) #i+1:每个数字在每个组合中只能使用一次
sum -= candidates[i] #回溯
path.pop() #回溯
candidates = sorted(candidates) #首先把给candidates排序,让其相同的元素都挨在一起。
backtrack(candidates,target,0,0)
return res
```
Go Go
javaScript
```js
/**
* @param {number[]} candidates
* @param {number} target
* @return {number[][]}
*/
var combinationSum2 = function(candidates, target) {
const res = []; path = [], len = candidates.length;
candidates.sort();
backtracking(0, 0);
return res;
function backtracking(sum, i) {
if (sum > target) return;
if (sum === target) {
res.push(Array.from(path));
return;
}
let f = -1;
for(let j = i; j < len; j++) {
const n = candidates[j];
if(n > target - sum || n === f) continue;
path.push(n);
sum += n;
f = n;
backtracking(sum, j + 1);
path.pop();
sum -= n;
}
}
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 相对于[贪心算法:跳跃游戏](https://mp.weixin.qq.com/s/606_N9j8ACKCODoCbV1lSA)难了不少,做好心里准备! > 相对于[贪心算法:跳跃游戏](https://mp.weixin.qq.com/s/606_N9j8ACKCODoCbV1lSA)难了不少,做好心里准备!
@ -175,9 +175,64 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def jump(self, nums: List[int]) -> int:
if len(nums) == 1: return 0
ans = 0
curDistance = 0
nextDistance = 0
for i in range(len(nums)):
nextDistance = max(i + nums[i], nextDistance)
if i == curDistance:
if curDistance != len(nums) - 1:
ans += 1
curDistance = nextDistance
if nextDistance >= len(nums) - 1: break
return ans
```
Go Go
```Go
func jump(nums []int) int {
dp:=make([]int ,len(nums))
dp[0]=0
for i:=1;i<len(nums);i++{
dp[i]=i
for j:=0;j<i;j++{
if nums[j]+j>i{
dp[i]=min(dp[j]+1,dp[i])
}
}
}
return dp[len(nums)-1]
}
```
Javascript:
```Javascript
var jump = function(nums) {
let curIndex = 0
let nextIndex = 0
let steps = 0
for(let i = 0; i < nums.length - 1; i++) {
nextIndex = Math.max(nums[i] + i, nextIndex)
if(i === curIndex) {
curIndex = nextIndex
steps++
}
}
return steps
};
```
/*
dp[i]表示从起点到当前位置的最小跳跃次数
dp[i]=min(dp[j]+1,dp[i]) 表示从j位置用一步跳跃到当前位置这个j位置可能有很多个却最小一个就可以
*/
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 46.全排列 ## 46.全排列
@ -149,6 +149,7 @@ public:
Java Java
```java ```java
class Solution { class Solution {
List<List<Integer>> result = new ArrayList<>();// 存放符合条件结果的集合 List<List<Integer>> result = new ArrayList<>();// 存放符合条件结果的集合
LinkedList<Integer> path = new LinkedList<>();// 用来存放符合条件结果 LinkedList<Integer> path = new LinkedList<>();// 用来存放符合条件结果
boolean[] used; boolean[] used;
@ -167,9 +168,6 @@ class Solution {
return; return;
} }
for (int i = 0; i < nums.length; i++){ for (int i = 0; i < nums.length; i++){
// if (path.contains(nums[i])){
// continue;
// }
if (used[i]){ if (used[i]){
continue; continue;
} }
@ -184,7 +182,45 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def permute(self, nums: List[int]) -> List[List[int]]:
res = [] #存放符合条件结果的集合
path = [] #用来存放符合条件的结果
used = [] #用来存放已经用过的数字
def backtrack(nums,used):
if len(path) == len(nums):
return res.append(path[:]) #此时说明找到了一组
for i in range(0,len(nums)):
if nums[i] in used:
continue #used里已经收录的元素,直接跳过
path.append(nums[i])
used.append(nums[i])
backtrack(nums,used)
used.pop()
path.pop()
backtrack(nums,used)
return res
```
Python优化不用used数组
```python3
class Solution:
def permute(self, nums: List[int]) -> List[List[int]]:
res = [] #存放符合条件结果的集合
path = [] #用来存放符合条件的结果
def backtrack(nums):
if len(path) == len(nums):
return res.append(path[:]) #此时说明找到了一组
for i in range(0,len(nums)):
if nums[i] in path: #path里已经收录的元素,直接跳过
continue
path.append(nums[i])
backtrack(nums) #递归
path.pop() #回溯
backtrack(nums)
return res
```
Go Go
```Go ```Go
@ -208,14 +244,33 @@ func backtrack(nums,pathNums []int,used []bool){
} }
} }
func permute(nums []int) [][]int { Javascript:
//var pathNums []int
pathNums:=make([]int,0) ```javascript
var used=make([]bool,len(nums))
result=[][]int{} var permute = function(nums) {
backtrack(nums,pathNums,used) let result = []
return result let path = []
function backtracing(used) {
if(path.length === nums.length) {
result.push(path.slice(0))
return
} }
for(let i = 0; i < nums.length; i++) {
if(used[nums[i]]) {
continue
}
used[nums[i]] = true
path.push(nums[i])
backtracing(used)
path.pop()
used[nums[i]] = false
}
}
backtracing([])
return result
};
``` ```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 排列问题(二) # 排列问题(二)
## 47.全排列 II ## 47.全排列 II
@ -85,7 +85,7 @@ public:
path.clear(); path.clear();
sort(nums.begin(), nums.end()); // 排序 sort(nums.begin(), nums.end()); // 排序
vector<bool> used(nums.size(), false); vector<bool> used(nums.size(), false);
backtracking(nums, vec, used); backtracking(nums, used);
return result; return result;
} }
}; };
@ -220,6 +220,43 @@ class Solution:
return res return res
``` ```
Javascript:
```javascript
var permuteUnique = function (nums) {
nums.sort((a, b) => {
return a - b
})
let result = []
let path = []
function backtracing( used) {
if (path.length === nums.length) {
result.push(path.slice())
return
}
for (let i = 0; i < nums.length; i++) {
if (i > 0 && nums[i] === nums[i - 1] && !used[i - 1]) {
continue
}
if (!used[i]) {
used[i] = true
path.push(nums[i])
backtracing(used)
path.pop()
used[i] = false
}
}
}
backtracing([])
return result
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 第51题. N皇后 ## 第51题. N皇后
@ -430,6 +430,65 @@ func solveNQueens(n int) [][]string {
} }
``` ```
Javascript:
```Javascript
var solveNQueens = function(n) {
function isValid(row, col, chessBoard, n) {
for(let i = 0; i < row; i++) {
if(chessBoard[i][col] === 'Q') {
return false
}
}
for(let i = row - 1, j = col - 1; i >= 0 && j >= 0; i--, j--) {
if(chessBoard[i][j] === 'Q') {
return false
}
}
for(let i = row - 1, j = col + 1; i >= 0 && j < n; i--, j++) {
if(chessBoard[i][j] === 'Q') {
return false
}
}
return true
}
function transformChessBoard(chessBoard) {
let chessBoardBack = []
chessBoard.forEach(row => {
let rowStr = ''
row.forEach(value => {
rowStr += value
})
chessBoardBack.push(rowStr)
})
return chessBoardBack
}
let result = []
function backtracing(row,chessBoard) {
if(row === n) {
result.push(transformChessBoard(chessBoard))
return
}
for(let col = 0; col < n; col++) {
if(isValid(row, col, chessBoard, n)) {
chessBoard[row][col] = 'Q'
backtracing(row + 1,chessBoard)
chessBoard[row][col] = '.'
}
}
}
let chessBoard = new Array(n).fill([]).map(() => new Array(n).fill('.'))
backtracing(0,chessBoard)
return result
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 53. 最大子序和 ## 53. 最大子序和
@ -175,29 +175,39 @@ class Solution:
``` ```
Go Go
```Go
func maxSubArray(nums []int) int {
if len(nums)<1{
return 0
}
dp:=make([]int,len(nums))
result:=nums[0]
dp[0]=nums[0]
for i:=1;i<len(nums);i++{
dp[i]=max(dp[i-1]+nums[i],nums[i])
result=max(dp[i],result)
}
return result
}
func max(a,b int)int{ ```go
if a>b{ func maxSubArray(nums []int) int {
return a maxSum := nums[0]
}else{ for i := 1; i < len(nums); i++ {
return b if nums[i] + nums[i-1] > nums[i] {
nums[i] += nums[i-1]
} }
if nums[i] > maxSum {
maxSum = nums[i]
}
}
return maxSum
} }
``` ```
Javascript:
```Javascript
var maxSubArray = function(nums) {
let result = -Infinity
let count = 0
for(let i = 0; i < nums.length; i++) {
count += nums[i]
if(count > result) {
result = count
}
if(count < 0) {
count = 0
}
}
return result
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 53. 最大子序和 ## 53. 最大子序和
@ -95,10 +95,47 @@ public:
Java Java
```java
/**
* 1.dp[i]代表当前下标对应的最大值
* 2.递推公式 dp[i] = max (dp[i-1]+nums[i],nums[i]) res = max(res,dp[i])
* 3.初始化 都为 0
* 4.遍历方向,从前往后
* 5.举例推导结果。。。
*
* @param nums
* @return
*/
public static int maxSubArray(int[] nums) {
if (nums.length == 0) {
return 0;
}
int res = nums[0];
int[] dp = new int[nums.length];
dp[0] = nums[0];
for (int i = 1; i < nums.length; i++) {
dp[i] = Math.max(dp[i - 1] + nums[i], nums[i]);
res = res > dp[i] ? res : dp[i];
}
return res;
}
```
Python Python
```python
class Solution:
def maxSubArray(self, nums: List[int]) -> int:
if len(nums) == 0:
return 0
dp = [0] * len(nums)
dp[0] = nums[0]
result = dp[0]
for i in range(1, len(nums)):
dp[i] = max(dp[i-1] + nums[i], nums[i]) #状态转移公式
result = max(result, dp[i]) #result 保存dp[i]的最大值
return result
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 55. 跳跃游戏 ## 55. 跳跃游戏
@ -122,8 +122,39 @@ class Solution:
``` ```
Go Go
```Go
func canJUmp(nums []int) bool {
if len(nums)<=1{
return true
}
dp:=make([]bool,len(nums))
dp[0]=true
for i:=1;i<len(nums);i++{
for j:=i-1;j>=0;j--{
if dp[j]&&nums[j]+j>=i{
dp[i]=true
break
}
}
}
return dp[len(nums)-1]
}
```
Javascript:
```Javascript
var canJump = function(nums) {
if(nums.length === 1) return true
let cover = 0
for(let i = 0; i <= cover; i++) {
cover = Math.max(cover, i + nums[i])
if(cover >= nums.length - 1) {
return true
}
}
return false
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 56. 合并区间 ## 56. 合并区间
@ -141,16 +141,7 @@ Java
class Solution { class Solution {
public int[][] merge(int[][] intervals) { public int[][] merge(int[][] intervals) {
List<int[]> res = new LinkedList<>(); List<int[]> res = new LinkedList<>();
Arrays.sort(intervals, new Comparator<int[]>() { Arrays.sort(intervals, (o1, o2) -> Integer.compare(o1[0], o2[0]));
@Override
public int compare(int[] o1, int[] o2) {
if (o1[0] != o2[0]) {
return Integer.compare(o1[0],o2[0]);
} else {
return Integer.compare(o1[1],o2[1]);
}
}
});
int start = intervals[0][0]; int start = intervals[0][0];
for (int i = 1; i < intervals.length; i++) { for (int i = 1; i < intervals.length; i++) {
@ -168,10 +159,69 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def merge(self, intervals: List[List[int]]) -> List[List[int]]:
if len(intervals) == 0: return intervals
intervals.sort(key=lambda x: x[0])
result = []
result.append(intervals[0])
for i in range(1, len(intervals)):
last = result[-1]
if last[1] >= intervals[i][0]:
result[-1] = [last[0], max(last[1], intervals[i][1])]
else:
result.append(intervals[i])
return result
```
Go Go
```Go
func merge(intervals [][]int) [][]int {
sort.Slice(intervals, func(i, j int) bool {
return intervals[i][0]<intervals[j][0]
})
res:=[][]int{}
prev:=intervals[0]
for i:=1;i<len(intervals);i++{
cur :=intervals[i]
if prev[1]<cur[0]{
res=append(res,prev)
prev=cur
}else {
prev[1]=max(prev[1],cur[1])
}
}
res=append(res,prev)
return res
}
func max(a, b int) int {
if a > b { return a }
return b
}
```
Javascript
```javascript
var merge = function (intervals) {
intervals.sort((a, b) => a[0] - b[0]);
let prev = intervals[0]
let result = []
for(let i =0; i<intervals.length; i++){
let cur = intervals[i]
if(cur[0] > prev[1]){
result.push(prev)
prev = cur
}else{
prev[1] = Math.max(cur[1],prev[1])
}
}
result.push(prev)
return result
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -224,6 +224,88 @@ class Solution:
return matrix return matrix
``` ```
javaScript
```js
/**
* @param {number} n
* @return {number[][]}
*/
var generateMatrix = function(n) {
// new Array(n).fill(new Array(n))
// 使用fill --> 填充的是同一个数组地址
const res = Array.from({length: n}).map(() => new Array(n));
let loop = n >> 1, i = 0, //循环次数
count = 1,
startX = startY = 0; // 起始位置
while(++i <= loop) {
// 定义行列
let row = startX, column = startY;
// [ startY, n - i)
while(column < n - i) {
res[row][column++] = count++;
}
// [ startX, n - i)
while(row < n - i) {
res[row++][column] = count++;
}
// [n - i , startY)
while(column > startY) {
res[row][column--] = count++;
}
// [n - i , startX)
while(row > startX) {
res[row--][column] = count++;
}
startX = ++startY;
}
if(n & 1) {
res[startX][startY] = count;
}
return res;
};
```
Go:
```go
func generateMatrix(n int) [][]int {
top, bottom := 0, n-1
left, right := 0, n-1
num := 1
tar := n * n
matrix := make([][]int, n)
for i := 0; i < n; i++ {
matrix[i] = make([]int, n)
}
for num <= tar {
for i := left; i <= right; i++ {
matrix[top][i] = num
num++
}
top++
for i := top; i <= bottom; i++ {
matrix[i][right] = num
num++
}
right--
for i := right; i >= left; i-- {
matrix[bottom][i] = num
num++
}
bottom--
for i := bottom; i >= top; i-- {
matrix[i][left] = num
num++
}
left++
}
return matrix
}
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 62.不同路径 ## 62.不同路径
@ -86,7 +86,7 @@ public:
### 动态规划 ### 动态规划
机器人从(0 , 0) 位置发,到(m - 1, n - 1)终点。 机器人从(0 , 0) 位置发,到(m - 1, n - 1)终点。
按照动规五部曲来分析: 按照动规五部曲来分析:
@ -243,14 +243,92 @@ public:
Java Java
```java
/**
* 1. 确定dp数组下表含义 dp[i][j] 到每一个坐标可能的路径种类
* 2. 递推公式 dp[i][j] = dp[i-1][j] dp[i][j-1]
* 3. 初始化 dp[i][0]=1 dp[0][i]=1 初始化横竖就可
* 4. 遍历顺序 一行一行遍历
* 5. 推导结果 。。。。。。。。
*
* @param m
* @param n
* @return
*/
public static int uniquePaths(int m, int n) {
int[][] dp = new int[m][n];
//初始化
for (int i = 0; i < m; i++) {
dp[i][0] = 1;
}
for (int i = 0; i < n; i++) {
dp[0][i] = 1;
}
for (int i = 1; i < m; i++) {
for (int j = 1; j < n; j++) {
dp[i][j] = dp[i-1][j]+dp[i][j-1];
}
}
return dp[m-1][n-1];
}
```
Python Python
```python
class Solution: # 动态规划
def uniquePaths(self, m: int, n: int) -> int:
dp = [[0 for i in range(n)] for j in range(m)]
for i in range(m): dp[i][0] = 1
for j in range(n): dp[0][j] = 1
for i in range(1, m):
for j in range(1, n):
dp[i][j] = dp[i][j - 1] + dp[i - 1][j]
return dp[m - 1][n - 1]
```
Go Go
```Go
func uniquePaths(m int, n int) int {
dp := make([][]int, m)
for i := range dp {
dp[i] = make([]int, n)
dp[i][0] = 1
}
for j := 0; j < n; j++ {
dp[0][j] = 1
}
for i := 1; i < m; i++ {
for j := 1; j < n; j++ {
dp[i][j] = dp[i-1][j] + dp[i][j-1]
}
}
return dp[m-1][n-1]
}
```
Javascript
```Javascript
var uniquePaths = function(m, n) {
const dp = Array(m).fill().map(item => Array(n))
for (let i = 0; i < m; ++i) {
dp[i][0] = 1
}
for (let i = 0; i < n; ++i) {
dp[0][i] = 1
}
for (let i = 1; i < m; ++i) {
for (let j = 1; j < n; ++j) {
dp[i][j] = dp[i - 1][j] + dp[i][j - 1]
}
}
return dp[m - 1][n - 1]
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 63. 不同路径 II ## 63. 不同路径 II
@ -157,8 +157,6 @@ public:
* 时间复杂度O(n * m) n m 分别为obstacleGrid 长度和宽度 * 时间复杂度O(n * m) n m 分别为obstacleGrid 长度和宽度
* 空间复杂度O(n * m) * 空间复杂度O(n * m)
至于能不能优化空间降为一维dp数组我感觉不太行因为要考虑障碍如果把这些障碍压缩到一行结果一定就不一样了。
## 总结 ## 总结
本题是[62.不同路径](https://mp.weixin.qq.com/s/MGgGIt4QCpFMROE9X9he_A)的障碍版,整体思路大体一致。 本题是[62.不同路径](https://mp.weixin.qq.com/s/MGgGIt4QCpFMROE9X9he_A)的障碍版,整体思路大体一致。
@ -237,7 +235,74 @@ class Solution:
Go Go
```go
func uniquePathsWithObstacles(obstacleGrid [][]int) int {
m,n:= len(obstacleGrid),len(obstacleGrid[0])
// 定义一个dp数组
dp := make([][]int,m)
for i,_ := range dp {
dp[i] = make([]int,n)
}
// 初始化
for i:=0;i<m;i++ {
// 如果是障碍物, 后面的就都是0, 不用循环了
if obstacleGrid[i][0] == 1 {
break
}
dp[i][0]=1
}
for i:=0;i<n;i++ {
if obstacleGrid[0][i] == 1 {
break
}
dp[0][i]=1
}
// dp数组推导过程
for i:=1;i<m;i++ {
for j:=1;j<n;j++ {
// 如果obstacleGrid[i][j]这个点是障碍物, 那么我们的dp[i][j]保持为0
if obstacleGrid[i][j] != 1 {
// 否则我们需要计算当前点可以到达的路径数
dp[i][j] = dp[i-1][j]+dp[i][j-1]
}
}
}
// debug遍历dp
//for i,_ := range dp {
// for j,_ := range dp[i] {
// fmt.Printf("%.2v,",dp[i][j])
// }
// fmt.Println()
//}
return dp[m-1][n-1]
}
```
Javascript
``` Javascript
var uniquePathsWithObstacles = function(obstacleGrid) {
const m = obstacleGrid.length
const n = obstacleGrid[0].length
const dp = Array(m).fill().map(item => Array(n).fill(0))
for (let i = 0; i < m && obstacleGrid[i][0] === 0; ++i) {
dp[i][0] = 1
}
for (let i = 0; i < n && obstacleGrid[0][i] === 0; ++i) {
dp[0][i] = 1
}
for (let i = 1; i < m; ++i) {
for (let j = 1; j < n; ++j) {
dp[i][j] = obstacleGrid[i][j] === 1 ? 0 : dp[i - 1][j] + dp[i][j - 1]
}
}
return dp[m - 1][n - 1]
};
```
----------------------- -----------------------

View File

@ -1,14 +1,15 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 70. 爬楼梯 ## 70. 爬楼梯
题目地址https://leetcode-cn.com/problems/climbing-stairs/
假设你正在爬楼梯。需要 n 阶你才能到达楼顶。 假设你正在爬楼梯。需要 n 阶你才能到达楼顶。
每次你可以爬 1 或 2 个台阶。你有多少种不同的方法可以爬到楼顶呢? 每次你可以爬 1 或 2 个台阶。你有多少种不同的方法可以爬到楼顶呢?
@ -212,7 +213,45 @@ public:
Java Java
```Java
class Solution {
public int climbStairs(int n) {
// 跟斐波那契数列一样
if(n <= 2) return n;
int a = 1, b = 2, sum = 0;
for(int i = 3; i <= n; i++){
sum = a + b;
a = b;
b = sum;
}
return b;
}
}
```
```java
// 常规方式
public int climbStairs(int n) {
int[] dp = new int[n + 1];
dp[0] = 1;
dp[1] = 1;
for (int i = 2; i <= n; i++) {
dp[i] = dp[i - 1] + dp[i - 2];
}
return dp[n];
}
// 用变量记录代替数组
public int climbStairs(int n) {
int a = 0, b = 1, c = 0; // 默认需要1次
for (int i = 1; i <= n; i++) {
c = a + b; // f(i - 1) + f(n - 2)
a = b; // 记录上一轮的值
b = c; // 向后步进1个数
}
return c;
}
```
Python Python

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 动态规划:以前我没得选,现在我选择再爬一次! # 动态规划:以前我没得选,现在我选择再爬一次!
之前讲这道题目的时候,因为还没有讲背包问题,所以就只是讲了一下爬楼梯最直接的动规方法(斐波那契)。 之前讲这道题目的时候,因为还没有讲背包问题,所以就只是讲了一下爬楼梯最直接的动规方法(斐波那契)。
@ -149,9 +149,44 @@ class Solution {
Python Python
Go ```python3
class Solution:
def climbStairs(self, n: int) -> int:
dp = [0]*(n + 1)
dp[0] = 1
m = 2
# 遍历背包
for j in range(n + 1):
# 遍历物品
for step in range(1, m + 1):
if j >= step:
dp[j] += dp[j - step]
return dp[n]
```
Go
```go
func climbStairs(n int) int {
//定义
dp := make([]int, n+1)
//初始化
dp[0] = 1
// 本题物品只有两个1,2
m := 2
// 遍历顺序
for j := 1; j <= n; j++ { //先遍历背包
for i := 1; i <= m; i++ { //再遍历物品
if j >= i {
dp[j] += dp[j-i]
}
//fmt.Println(dp)
}
}
return dp[n]
}
```
----------------------- -----------------------

View File

@ -1,13 +1,15 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 72. 编辑距离 ## 72. 编辑距离
https://leetcode-cn.com/problems/edit-distance/
给你两个单词 word1 和 word2请你计算出将 word1 转换成 word2 所使用的最少操作数 。 给你两个单词 word1 和 word2请你计算出将 word1 转换成 word2 所使用的最少操作数 。
你可以对一个单词进行如下三种操作: 你可以对一个单词进行如下三种操作:
@ -198,10 +200,50 @@ public:
Java Java
```java
public int minDistance(String word1, String word2) {
int m = word1.length();
int n = word2.length();
int[][] dp = new int[m + 1][n + 1];
// 初始化
for (int i = 1; i <= m; i++) {
dp[i][0] = i;
}
for (int j = 1; j <= n; j++) {
dp[0][j] = j;
}
for (int i = 1; i <= m; i++) {
for (int j = 1; j <= n; j++) {
// 因为dp数组有效位从1开始
// 所以当前遍历到的字符串的位置为i-1 | j-1
if (word1.charAt(i - 1) == word2.charAt(j - 1)) {
dp[i][j] = dp[i - 1][j - 1];
} else {
dp[i][j] = Math.min(Math.min(dp[i - 1][j - 1], dp[i][j - 1]), dp[i - 1][j]) + 1;
}
}
}
return dp[m][n];
}
```
Python Python
```python
class Solution:
def minDistance(self, word1: str, word2: str) -> int:
dp = [[0] * (len(word2)+1) for _ in range(len(word1)+1)]
for i in range(len(word1)+1):
dp[i][0] = i
for j in range(len(word2)+1):
dp[0][j] = j
for i in range(1, len(word1)+1):
for j in range(1, len(word2)+1):
if word1[i-1] == word2[j-1]:
dp[i][j] = dp[i-1][j-1]
else:
dp[i][j] = min(dp[i-1][j-1], dp[i-1][j], dp[i][j-1]) + 1
return dp[-1][-1]
```
Go Go
```Go ```Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -370,11 +370,70 @@ class Solution {
Python Python
```python3
class Solution:
def combine(self, n: int, k: int) -> List[List[int]]:
res=[] #存放符合条件结果的集合
path=[] #用来存放符合条件结果
def backtrack(n,k,startIndex):
if len(path) == k:
res.append(path[:])
return
for i in range(startIndex,n+1):
path.append(i) #处理节点
backtrack(n,k,i+1) #递归
path.pop() #回溯,撤销处理的节点
backtrack(n,k,1)
return res
```
javascript
```javascript
let result = []
let path = []
var combine = function(n, k) {
result = []
combineHelper(n, k, 1)
return result
};
const combineHelper = (n, k, startIndex) => {
if (path.length === k) {
result.push([...path])
return
}
for (let i = startIndex; i <= n - (k - path.length) + 1; ++i) {
path.push(i)
combineHelper(n, k, i + 1)
path.pop()
}
}
```
Go Go
```Go
var res [][]int
func combine(n int, k int) [][]int {
res=[][]int{}
if n <= 0 || k <= 0 || k > n {
return res
}
backtrack(n, k, 1, []int{})
return res
}
func backtrack(n,k,start int,track []int){
if len(track)==k{
temp:=make([]int,k)
copy(temp,track)
res=append(res,temp)
}
if len(track)+n-start+1 < k {
return
}
for i:=start;i<=n;i++{
track=append(track,i)
backtrack(n,k,i+1,track)
track=track[:len(track)-1]
}
}
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -147,7 +147,7 @@ public:
Java Java
``` ```java
class Solution { class Solution {
List<List<Integer>> result = new ArrayList<>(); List<List<Integer>> result = new ArrayList<>();
LinkedList<Integer> path = new LinkedList<>(); LinkedList<Integer> path = new LinkedList<>();
@ -176,9 +176,71 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def combine(self, n: int, k: int) -> List[List[int]]:
res=[] #存放符合条件结果的集合
path=[] #用来存放符合条件结果
def backtrack(n,k,startIndex):
if len(path) == k:
res.append(path[:])
return
for i in range(startIndex,n-(k-len(path))+2): #优化的地方
path.append(i) #处理节点
backtrack(n,k,i+1) #递归
path.pop() #回溯,撤销处理的节点
backtrack(n,k,1)
return res
```
Go Go
```Go
var res [][]int
func combine(n int, k int) [][]int {
res=[][]int{}
if n <= 0 || k <= 0 || k > n {
return res
}
backtrack(n, k, 1, []int{})
return res
}
func backtrack(n,k,start int,track []int){
if len(track)==k{
temp:=make([]int,k)
copy(temp,track)
res=append(res,temp)
}
if len(track)+n-start+1 < k {
return
}
for i:=start;i<=n;i++{
track=append(track,i)
backtrack(n,k,i+1,track)
track=track[:len(track)-1]
}
}
```
javaScript:
```js
var combine = function(n, k) {
const res = [], path = [];
backtracking(n, k, 1);
return res;
function backtracking (n, k, i){
const len = path.length;
if(len === k) {
res.push(Array.from(path));
return;
}
for(let a = i; a <= n + len - k + 1; a++) {
path.push(a);
backtracking(n, k, a + 1);
path.pop();
}
}
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 第78题. 子集 ## 第78题. 子集
@ -186,7 +186,6 @@ class Solution {
result.add(new ArrayList<>()); result.add(new ArrayList<>());
return result; return result;
} }
Arrays.sort(nums);
subsetsHelper(nums, 0); subsetsHelper(nums, 0);
return result; return result;
} }
@ -206,7 +205,20 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def subsets(self, nums: List[int]) -> List[List[int]]:
res = []
path = []
def backtrack(nums,startIndex):
res.append(path[:]) #收集子集,要放在终止添加的上面,否则会漏掉自己
for i in range(startIndex,len(nums)): #当startIndex已经大于数组的长度了就终止了for循环本来也结束了所以不需要终止条件
path.append(nums[i])
backtrack(nums,i+1) #递归
path.pop() #回溯
backtrack(nums,0)
return res
```
Go Go
```Go ```Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 第90题.子集II ## 第90题.子集II
@ -208,7 +208,23 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def subsetsWithDup(self, nums: List[int]) -> List[List[int]]:
res = [] #存放符合条件结果的集合
path = [] #用来存放符合条件结果
def backtrack(nums,startIndex):
res.append(path[:])
for i in range(startIndex,len(nums)):
if i > startIndex and nums[i] == nums[i - 1]: #我们要对同一树层使用过的元素进行跳过
continue
path.append(nums[i])
backtrack(nums,i+1) #递归
path.pop() #回溯
nums = sorted(nums) #去重需要排序
backtrack(nums,0)
return res
```
Go Go
```Go ```Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -338,6 +338,35 @@ class Solution(object):
return ans``` return ans```
``` ```
JavaScript
```js
/**
* @param {string} s
* @return {string[]}
*/
var restoreIpAddresses = function(s) {
const res = [], path = [];
backtracking(0, 0)
return res;
function backtracking(i) {
const len = path.length;
if(len > 4) return;
if(len === 4 && i === s.length) {
res.push(path.join("."));
return;
}
for(let j = i; j < s.length; j++) {
const str = s.substr(i, j - i + 1);
if(str.length > 3 || +str > 255) break;
if(str.length > 1 && str[0] === "0") break;
path.push(str);
backtracking(j + 1);
path.pop()
}
}
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 96.不同的二叉搜索树 ## 96.不同的二叉搜索树
@ -186,10 +186,30 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def numTrees(self, n: int) -> int:
dp = [0] * (n + 1)
dp[0], dp[1] = 1, 1
for i in range(2, n + 1):
for j in range(1, i + 1):
dp[i] += dp[j - 1] * dp[i - j]
return dp[-1]
```
Go Go
```Go
func numTrees(n int)int{
dp:=make([]int,n+1)
dp[0]=1
for i:=1;i<=n;i++{
for j:=1;j<=i;j++{
dp[i]+=dp[j-1]*dp[i-j]
}
}
return dp[n]
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 98.验证二叉搜索树 ## 98.验证二叉搜索树
@ -304,11 +304,58 @@ class Solution {
return true; return true;
} }
} }
// 简洁实现·递归解法
class Solution {
public boolean isValidBST(TreeNode root) {
return validBST(Long.MIN_VALUE, Long.MAX_VALUE, root);
}
boolean validBST(long lower, long upper, TreeNode root) {
if (root == null) return true;
if (root.val <= lower || root.val >= upper) return false;
return validBST(lower, root.val, root.left) && validBST(root.val, upper, root.right);
}
}
// 简洁实现·中序遍历
class Solution {
private long prev = Long.MIN_VALUE;
public boolean isValidBST(TreeNode root) {
if (root == null) {
return true;
}
if (!isValidBST(root.left)) {
return false;
}
if (root.val <= prev) { // 不满足二叉搜索树条件
return false;
}
prev = root.val;
return isValidBST(root.right);
}
}
``` ```
Python Python
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
//递归法
class Solution:
def isValidBST(self, root: TreeNode) -> bool:
res = [] //把二叉搜索树按中序遍历写成list
def buildalist(root):
if not root: return
buildalist(root.left) //左
res.append(root.val) //中
buildalist(root.right) //右
return res
buildalist(root)
return res == sorted(res) and len(set(res)) == len(res) //检查list里的数有没有重复元素以及是否按从小到大排列
```
Go Go
```Go ```Go
import "math" import "math"

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 101. 对称二叉树 ## 101. 对称二叉树
@ -360,9 +360,129 @@ Java
Python Python
> 递归法
```python
class Solution:
def isSymmetric(self, root: TreeNode) -> bool:
if not root:
return True
return self.compare(root.left, root.right)
def compare(self, left, right):
#首先排除空节点的情况
if left == None and right != None: return False
elif left != None and right == None: return False
elif left == None and right == None: return True
#排除了空节点,再排除数值不相同的情况
elif left.val != right.val: return False
#此时就是:左右节点都不为空,且数值相同的情况
#此时才做递归,做下一层的判断
outside = self.compare(left.left, right.right) #左子树:左、 右子树:右
inside = self.compare(left.right, right.left) #左子树:右、 右子树:左
isSame = outside and inside #左子树:中、 右子树:中 (逻辑处理)
return isSame
```
> 迭代法: 使用队列
```python
import collections
class Solution:
def isSymmetric(self, root: TreeNode) -> bool:
if not root:
return True
queue = collections.deque()
queue.append(root.left) #将左子树头结点加入队列
queue.append(root.right) #将右子树头结点加入队列
while queue: #接下来就要判断这这两个树是否相互翻转
leftNode = queue.popleft()
rightNode = queue.popleft()
if not leftNode and not rightNode: #左节点为空、右节点为空,此时说明是对称的
continue
#左右一个节点不为空或者都不为空但数值不相同返回false
if not leftNode or not rightNode or leftNode.val != rightNode.val:
return False
queue.append(leftNode.left) #加入左节点左孩子
queue.append(rightNode.right) #加入右节点右孩子
queue.append(leftNode.right) #加入左节点右孩子
queue.append(rightNode.left) #加入右节点左孩子
return True
```
> 迭代法:使用栈
```python
class Solution:
def isSymmetric(self, root: TreeNode) -> bool:
if not root:
return True
st = [] #这里改成了栈
st.append(root.left)
st.append(root.right)
while st:
leftNode = st.pop()
rightNode = st.pop()
if not leftNode and not rightNode:
continue
if not leftNode or not rightNode or leftNode.val != rightNode.val:
return False
st.append(leftNode.left)
st.append(rightNode.right)
st.append(leftNode.right)
st.append(rightNode.left)
return True
```
Go Go
```go
/**
* Definition for a binary tree node.
* type TreeNode struct {
* Val int
* Left *TreeNode
* Right *TreeNode
* }
*/
// 递归
func defs(left *TreeNode, right *TreeNode) bool {
if left == nil && right == nil {
return true;
};
if left == nil || right == nil {
return false;
};
if left.Val != right.Val {
return false;
}
return defs(left.Left, right.Right) && defs(right.Left, left.Right);
}
func isSymmetric(root *TreeNode) bool {
return defs(root.Left, root.Right);
}
// 迭代
func isSymmetric(root *TreeNode) bool {
var queue []*TreeNode;
if root != nil {
queue = append(queue, root.Left, root.Right);
}
for len(queue) > 0 {
left := queue[0];
right := queue[1];
queue = queue[2:];
if left == nil && right == nil {
continue;
}
if left == nil || right == nil || left.Val != right.Val {
return false;
};
queue = append(queue, left.Left, right.Right, right.Left, left.Right);
}
return true;
}
```
JavaScript JavaScript
```javascript ```javascript
@ -379,6 +499,90 @@ const check = (leftPtr, rightPtr) => {
return leftPtr.val === rightPtr.val && check(leftPtr.left, rightPtr.right) && check(leftPtr.right, rightPtr.left) return leftPtr.val === rightPtr.val && check(leftPtr.left, rightPtr.right) && check(leftPtr.right, rightPtr.left)
} }
``` ```
JavaScript:
递归判断是否为对称二叉树:
```javascript
var isSymmetric = function(root) {
//使用递归遍历左右子树 递归三部曲
// 1. 确定递归的参数 root.left root.right和返回值true false
const compareNode=function(left,right){
//2. 确定终止条件 空的情况
if(left===null&&right!==null||left!==null&&right===null){
return false;
}else if(left===null&&right===null){
return true;
}else if(left.val!==right.val){
return false;
}
//3. 确定单层递归逻辑
let outSide=compareNode(left.left,right.right);
let inSide=compareNode(left.right,right.left);
return outSide&&inSide;
}
if(root===null){
return true;
}
return compareNode(root.left,root.right);
};
```
队列实现迭代判断是否为对称二叉树:
```javascript
var isSymmetric = function(root) {
//迭代方法判断是否是对称二叉树
//首先判断root是否为空
if(root===null){
return true;
}
let queue=[];
queue.push(root.left);
queue.push(root.right);
while(queue.length){
let leftNode=queue.shift();//左节点
let rightNode=queue.shift();//右节点
if(leftNode===null&&rightNode===null){
continue;
}
if(leftNode===null||rightNode===null||leftNode.val!==rightNode.val){
return false;
}
queue.push(leftNode.left);//左节点左孩子入队
queue.push(rightNode.right);//右节点右孩子入队
queue.push(leftNode.right);//左节点右孩子入队
queue.push(rightNode.left);//右节点左孩子入队
}
return true;
};
```
栈实现迭代判断是否为对称二叉树:
```javascript
var isSymmetric = function(root) {
//迭代方法判断是否是对称二叉树
//首先判断root是否为空
if(root===null){
return true;
}
let stack=[];
stack.push(root.left);
stack.push(root.right);
while(stack.length){
let rightNode=stack.pop();//左节点
let leftNode=stack.pop();//右节点
if(leftNode===null&&rightNode===null){
continue;
}
if(leftNode===null||rightNode===null||leftNode.val!==rightNode.val){
return false;
}
stack.push(leftNode.left);//左节点左孩子入队
stack.push(rightNode.right);//右节点右孩子入队
stack.push(leftNode.right);//左节点右孩子入队
stack.push(rightNode.left);//右节点左孩子入队
}
return true;
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 二叉树的层序遍历 # 二叉树的层序遍历
@ -79,6 +79,67 @@ public:
return result; return result;
} }
}; };
```
python代码
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
class Solution:
def levelOrder(self, root: TreeNode) -> List[List[int]]:
if not root:
return []
quene = [root]
out_list = []
while quene:
length = len(queue) # 这里一定要先求出队列的长度不能用range(len(queue))因为queue长度是变化的
in_list = []
for _ in range(length):
curnode = queue.pop(0) # (默认移除列表最后一个元素)这里需要移除队列最头上的那个
in_list.append(curnode.val)
if curnode.left: queue.append(curnode.left)
if curnode.right: queue.append(curnode.right)
out_list.append(in_list)
return out_list
```
javascript代码
```javascript
var levelOrder = function(root) {
//二叉树的层序遍历
let res=[],queue=[];
queue.push(root);
if(root===null){
return res;
}
while(queue.length!==0){
// 记录当前层级节点数
let length=queue.length;
//存放每一层的节点
let curLevel=[];
for(let i=0;i<length;i++){
let node=queue.shift();
curLevel.push(node.val);
// 存放当前层下一层的节点
node.left&&queue.push(node.left);
node.right&&queue.push(node.right);
}
//把每一层的结果放到结果数组
res.push(curLevel);
}
return res;
};
``` ```
**此时我们就掌握了二叉树的层序遍历了那么如下五道leetcode上的题目只需要修改模板的一两行代码不能再多了便可打倒** **此时我们就掌握了二叉树的层序遍历了那么如下五道leetcode上的题目只需要修改模板的一两行代码不能再多了便可打倒**
@ -122,6 +183,67 @@ public:
} }
}; };
``` ```
python代码
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
class Solution:
def levelOrderBottom(self, root: TreeNode) -> List[List[int]]:
if not root:
return []
quene = [root]
out_list = []
while quene:
in_list = []
for _ in range(len(quene)):
node = quene.pop(0)
in_list.append(node.val)
if node.left:
quene.append(node.left)
if node.right:
quene.append(node.right)
out_list.append(in_list)
out_list.reverse()
return out_list
# 执行用时36 ms, 在所有 Python3 提交中击败了92.00%的用户
# 内存消耗15.2 MB, 在所有 Python3 提交中击败了63.76%的用户
```
javascript代码
```javascript
var levelOrderBottom = function(root) {
let res=[],queue=[];
queue.push(root);
while(queue.length&&root!==null){
// 存放当前层级节点数组
let curLevel=[];
// 计算当前层级节点数量
let length=queue.length;
while(length--){
let node=queue.shift();
// 把当前层节点存入curLevel数组
curLevel.push(node.val);
// 把下一层级的左右节点存入queue队列
node.left&&queue.push(node.left);
node.right&&queue.push(node.right);
}
res.push(curLevel);
}
return res.reverse();
};
```
## 199.二叉树的右视图 ## 199.二叉树的右视图
@ -159,6 +281,73 @@ public:
} }
}; };
``` ```
python代码
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
class Solution:
def rightSideView(self, root: TreeNode) -> List[int]:
if not root:
return []
# deque来自collections模块不在力扣平台时需要手动写入
# 'from collections import deque' 导入
# deque相比list的好处是list的pop(0)是O(n)复杂度deque的popleft()是O(1)复杂度
quene = deque([root])
out_list = []
while quene:
# 每次都取最后一个node就可以了
node = quene[-1]
out_list.append(node.val)
# 执行这个遍历的目的是获取下一层所有的node
for _ in range(len(quene)):
node = quene.popleft()
if node.left:
quene.append(node.left)
if node.right:
quene.append(node.right)
return out_list
# 执行用时36 ms, 在所有 Python3 提交中击败了89.47%的用户
# 内存消耗14.6 MB, 在所有 Python3 提交中击败了96.65%的用户
```
javascript代码:
```javascript
var rightSideView = function(root) {
//二叉树右视图 只需要把每一层最后一个节点存储到res数组
let res=[],queue=[];
queue.push(root);
while(queue.length&&root!==null){
// 记录当前层级节点个数
let length=queue.length;
while(length--){
let node=queue.shift();
//length长度为0的时候表明到了层级最后一个节点
if(!length){
res.push(node.val);
}
node.left&&queue.push(node.left);
node.right&&queue.push(node.right);
}
}
return res;
};
```
## 637.二叉树的层平均值 ## 637.二叉树的层平均值
@ -199,6 +388,71 @@ public:
``` ```
python代码
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
class Solution:
def averageOfLevels(self, root: TreeNode) -> List[float]:
if not root:
return []
quene = deque([root])
out_list = []
while quene:
in_list = []
for _ in range(len(quene)):
node = quene.popleft()
in_list.append(node.val)
if node.left:
quene.append(node.left)
if node.right:
quene.append(node.right)
out_list.append(in_list)
out_list = map(lambda x: sum(x) / len(x), out_list)
return out_list
# 执行用时56 ms, 在所有 Python3 提交中击败了81.48%的用户
# 内存消耗17 MB, 在所有 Python3 提交中击败了89.68%的用户
```
javascript代码
```javascript
var averageOfLevels = function(root) {
//层级平均值
let res=[],queue=[];
queue.push(root);
while(queue.length&&root!==null){
//每一层节点个数
let length=queue.length;
//sum记录每一层的和
let sum=0;
for(let i=0;i<length;i++){
let node=queue.shift();
sum+=node.val;
node.left&&queue.push(node.left);
node.right&&queue.push(node.right);
}
//每一层的平均值存入数组res
res.push(sum/length);
}
return res;
};
```
## 429.N叉树的层序遍历 ## 429.N叉树的层序遍历
题目链接https://leetcode-cn.com/problems/n-ary-tree-level-order-traversal/ 题目链接https://leetcode-cn.com/problems/n-ary-tree-level-order-traversal/
@ -250,6 +504,92 @@ public:
}; };
``` ```
python代码
```python
"""
# Definition for a Node.
class Node:
def __init__(self, val=None, children=None):
self.val = val
self.children = children
"""
class Solution:
def levelOrder(self, root: 'Node') -> List[List[int]]:
if not root:
return []
quene = deque([root])
out_list = []
while quene:
in_list = []
for _ in range(len(quene)):
node = quene.popleft()
in_list.append(node.val)
if node.children:
# 这个地方要用extend而不是append我们看下面的例子
# In [18]: alist=[]
# In [19]: alist.append([1,2,3])
# In [20]: alist
# Out[20]: [[1, 2, 3]]
# In [21]: alist.extend([4,5,6])
# In [22]: alist
# Out[22]: [[1, 2, 3], 4, 5, 6]
# 可以看到extend对要添加的list进行了一个解包操作
# print(root.children)可以得到children是一个包含
# 孩子节点地址的list我们使用for遍历quene的时候
# 希望quene是一个单层list所以要用extend
# 使用extend的情况如果print(quene),结果是
# deque([<__main__.Node object at 0x7f60763ae0a0>])
# deque([<__main__.Node object at 0x7f607636e6d0>, <__main__.Node object at 0x7f607636e130>, <__main__.Node object at 0x7f607636e310>])
# deque([<__main__.Node object at 0x7f607636e880>, <__main__.Node object at 0x7f607636ef10>])
# 可以看到是单层list
# 如果使用appendprint(quene)的结果是
# deque([<__main__.Node object at 0x7f18907530a0>])
# deque([[<__main__.Node object at 0x7f18907136d0>, <__main__.Node object at 0x7f1890713130>, <__main__.Node object at 0x7f1890713310>]])
# 可以看到是两层list这样for的遍历就会报错
quene.extend(node.children)
out_list.append(in_list)
return out_list
# 执行用时60 ms, 在所有 Python3 提交中击败了76.99%的用户
# 内存消耗16.5 MB, 在所有 Python3 提交中击败了89.19%的用户
```
JavaScript代码
```JavaScript
var levelOrder = function(root) {
//每一层可能有2个以上,所以不再使用node.left node.right
let res=[],queue=[];
queue.push(root);
while(queue.length&&root!==null){
//记录每一层节点个数还是和二叉树一致
let length=queue.length;
//存放每层节点 也和二叉树一致
let curLevel=[];
while(length--){
let node = queue.shift();
curLevel.push(node.val);
//这里不再是 ndoe.left node.right 而是循坏node.children
for(let item of node.children){
item&&queue.push(item);
}
}
res.push(curLevel);
}
return res;
};
```
## 515.在每个树行中找最大值 ## 515.在每个树行中找最大值
题目链接https://leetcode-cn.com/problems/find-largest-value-in-each-tree-row/ 题目链接https://leetcode-cn.com/problems/find-largest-value-in-each-tree-row/
@ -287,6 +627,29 @@ public:
} }
}; };
``` ```
javascript代码
```javascript
var largestValues = function(root) {
//使用层序遍历
let res=[],queue=[];
queue.push(root);
while(root!==null&&queue.length){
//设置max初始值就是队列的第一个元素
let max=queue[0];
let length=queue.length;
while(length--){
let node = queue.shift();
max=max>node.val?max:node.val;
node.left&&queue.push(node.left);
node.right&&queue.push(node.right);
}
//把每一层的最大值放到res数组
res.push(max);
}
return res;
};
```
## 116.填充每个节点的下一个右侧节点指针 ## 116.填充每个节点的下一个右侧节点指针
@ -657,8 +1020,569 @@ Python
Go Go
```Go
func levelOrder(root *TreeNode) [][]int {
result:=make([][]int,0)
if root==nil{
return result
}
queue:=make([]*TreeNode,0)
queue=append(queue,root)
for len(queue)>0{
list:=make([]int,0)
l:=len(queue)
for i:=0;i<l;i++{
level:=queue[0]
queue=queue[1:]
list=append(list,level.Val)
if level.Left!=nil{
queue=append(queue,level.Left)
}
if level.Right!=nil{
queue=append(queue,level.Right)
}
}
result=append(result,list)
}
return result
}
```
> 二叉树的层序遍历GO语言完全版
```go
/**
102. 二叉树的层序遍历
*/
func levelOrder(root *TreeNode) [][]int {
res:=[][]int{}
if root==nil{//防止为空
return res
}
queue:=list.New()
queue.PushBack(root)
var tmpArr []int
for queue.Len()>0 {
length:=queue.Len()//保存当前层的长度,然后处理当前层(十分重要,防止添加下层元素影响判断层中元素的个数)
for i:=0;i<length;i++{
node:=queue.Remove(queue.Front()).(*TreeNode)//出队列
if node.Left!=nil{
queue.PushBack(node.Left)
}
if node.Right!=nil{
queue.PushBack(node.Right)
}
tmpArr=append(tmpArr,node.Val)//将值加入本层切片中
}
res=append(res,tmpArr)//放入结果集
tmpArr=[]int{}//清空层的数据
}
return res
}
/**
107. 二叉树的层序遍历 II
*/
func levelOrderBottom(root *TreeNode) [][]int {
queue:=list.New()
res:=[][]int{}
if root==nil{
return res
}
queue.PushBack(root)
for queue.Len()>0{
length:=queue.Len()
tmp:=[]int{}
for i:=0;i<length;i++{
node:=queue.Remove(queue.Front()).(*TreeNode)
if node.Left!=nil{
queue.PushBack(node.Left)
}
if node.Right!=nil{
queue.PushBack(node.Right)
}
tmp=append(tmp,node.Val)
}
res=append(res,tmp)
}
//反转结果集
for i:=0;i<len(res)/2;i++{
res[i],res[len(res)-i-1]=res[len(res)-i-1],res[i]
}
return res
}
/**
199. 二叉树的右视图
*/
func rightSideView(root *TreeNode) []int {
queue:=list.New()
res:=[][]int{}
var finaRes []int
if root==nil{
return finaRes
}
queue.PushBack(root)
for queue.Len()>0{
length:=queue.Len()
tmp:=[]int{}
for i:=0;i<length;i++{
node:=queue.Remove(queue.Front()).(*TreeNode)
if node.Left!=nil{
queue.PushBack(node.Left)
}
if node.Right!=nil{
queue.PushBack(node.Right)
}
tmp=append(tmp,node.Val)
}
res=append(res,tmp)
}
//取每一层的最后一个元素
for i:=0;i<len(res);i++{
finaRes=append(finaRes,res[i][len(res[i])-1])
}
return finaRes
}
/**
637. 二叉树的层平均值
*/
func averageOfLevels(root *TreeNode) []float64 {
res:=[][]int{}
var finRes []float64
if root==nil{//防止为空
return finRes
}
queue:=list.New()
queue.PushBack(root)
var tmpArr []int
for queue.Len()>0 {
length:=queue.Len()//保存当前层的长度,然后处理当前层(十分重要,防止添加下层元素影响判断层中元素的个数)
for i:=0;i<length;i++{
node:=queue.Remove(queue.Front()).(*TreeNode)//出队列
if node.Left!=nil{
queue.PushBack(node.Left)
}
if node.Right!=nil{
queue.PushBack(node.Right)
}
tmpArr=append(tmpArr,node.Val)//将值加入本层切片中
}
res=append(res,tmpArr)//放入结果集
tmpArr=[]int{}//清空层的数据
}
//计算每层的平均值
length:=len(res)
for i:=0;i<length;i++{
var sum int
for j:=0;j<len(res[i]);j++{
sum+=res[i][j]
}
tmp:=float64(sum)/float64(len(res[i]))
finRes=append(finRes,tmp)//将平均值放入结果集合
}
return finRes
}
/**
429. N 叉树的层序遍历
*/
func levelOrder(root *Node) [][]int {
queue:=list.New()
res:=[][]int{}//结果集
if root==nil{
return res
}
queue.PushBack(root)
for queue.Len()>0{
length:=queue.Len()//记录当前层的数量
var tmp []int
for T:=0;T<length;T++{//该层的每个元素一添加到该层的结果集中二找到该元素的下层元素加入到队列中方便下次使用
myNode:=queue.Remove(queue.Front()).(*Node)
tmp=append(tmp,myNode.Val)
for i:=0;i<len(myNode.Children);i++{
queue.PushBack(myNode.Children[i])
}
}
res=append(res,tmp)
}
return res
}
/**
515. 在每个树行中找最大值
*/
func largestValues(root *TreeNode) []int {
res:=[][]int{}
var finRes []int
if root==nil{//防止为空
return finRes
}
queue:=list.New()
queue.PushBack(root)
var tmpArr []int
//层次遍历
for queue.Len()>0 {
length:=queue.Len()//保存当前层的长度,然后处理当前层(十分重要,防止添加下层元素影响判断层中元素的个数)
for i:=0;i<length;i++{
node:=queue.Remove(queue.Front()).(*TreeNode)//出队列
if node.Left!=nil{
queue.PushBack(node.Left)
}
if node.Right!=nil{
queue.PushBack(node.Right)
}
tmpArr=append(tmpArr,node.Val)//将值加入本层切片中
}
res=append(res,tmpArr)//放入结果集
tmpArr=[]int{}//清空层的数据
}
//找到每层的最大值
for i:=0;i<len(res);i++{
finRes=append(finRes,max(res[i]...))
}
return finRes
}
func max(vals...int) int {
max:=int(math.Inf(-1))//负无穷
for _, val := range vals {
if val > max {
max = val
}
}
return max
}
/**
116. 填充每个节点的下一个右侧节点指针
117. 填充每个节点的下一个右侧节点指针 II
*/
func connect(root *Node) *Node {
res:=[][]*Node{}
if root==nil{//防止为空
return root
}
queue:=list.New()
queue.PushBack(root)
var tmpArr []*Node
for queue.Len()>0 {
length:=queue.Len()//保存当前层的长度,然后处理当前层(十分重要,防止添加下层元素影响判断层中元素的个数)
for i:=0;i<length;i++{
node:=queue.Remove(queue.Front()).(*Node)//出队列
if node.Left!=nil{
queue.PushBack(node.Left)
}
if node.Right!=nil{
queue.PushBack(node.Right)
}
tmpArr=append(tmpArr,node)//将值加入本层切片中
}
res=append(res,tmpArr)//放入结果集
tmpArr=[]*Node{}//清空层的数据
}
//遍历每层元素,指定next
for i:=0;i<len(res);i++{
for j:=0;j<len(res[i])-1;j++{
res[i][j].Next=res[i][j+1]
}
}
return root
}
```
Javascript:
```javascript
var levelOrder = function (root) {
let ans = [];
if (!root) return ans;
let queue = [root];
while (queue.length) {
let size = queue.length;
let temp = [];
while (size--) {
let n = queue.shift();
temp.push(n.val);
if (n.left) queue.push(n.left);
if (n.right) queue.push(n.right);
}
ans.push(temp);
}
return ans;
};
```
> 二叉树的层序遍历Javascript语言完全版 (迭代 + 递归)
```js
/**
* 102. 二叉树的层序遍历
* @param {TreeNode} root
* @return {number[][]}
*/
// 迭代
var levelOrder = function(root) {
const queue = [], res = [];
root && queue.push(root);
while(len = queue.length) {
const val = [];
while(len--) {
const node = queue.shift();
val.push(node.val);
node.left && queue.push(node.left);
node.right && queue.push(node.right);
}
res.push(val);
}
return res;
};
// 递归
var levelOrder = function(root) {
const res = [];
function defs (root, i) {
if(!root) return;
if(!res[i]) res[i] = [];
res[i].push(root.val)
root.left && defs(root.left, i + 1);
root.right && defs(root.right, i + 1);
}
defs(root, 0);
return res;
};
/**
* 107. 二叉树的层序遍历 II
* @param {TreeNode} root
* @return {number[][]}
*/
// 迭代
var levelOrderBottom = function(root) {
const queue = [], res = [];
root && queue.push(root);
while(len = queue.length) {
const val = [];
while(len--) {
const node = queue.shift();
val.push(node.val);
node.left && queue.push(node.left);
node.right && queue.push(node.right);
}
res.push(val);
}
return res.reverse()
};
// 递归
var levelOrderBottom = function(root) {
const res = [];
function defs (root, i) {
if(!root) return;
if(!res[i]) res[i] = [];
res[i].push(root.val);
root.left && defs(root.left, i + 1);
root.right && defs(root.right, i + 1);
}
defs(root, 0);
return res.reverse();
};
/**
* 199. 二叉树的右视图
* @param {TreeNode} root
* @return {number[]}
*/
// 迭代
var rightSideView = function(root) {
const res = [], queue = [];
root && queue.push(root);
while(l = queue.length) {
while (l--) {
const {val, left, right} = queue.shift();
!l && res.push(val);
left && queue.push(left);
right && queue.push(right);
}
}
return res;
};
// 递归
var rightSideView = function(root) {
const res = [];
function defs(root, i) {
if(!root) return;
res[i] = root.val;
root.left && defs(root.left, i + 1);
root.right && defs(root.right, i + 1);
}
defs(root, 0);
return res;
};
/**
* 637. 二叉树的层平均值
* @param {TreeNode} root
* @return {number[]}
*/
// 迭代
var averageOfLevels = function(root) {
const queue = [], res = [];
root && queue.push(root);
while(len = queue.length) {
let sum = 0, l = len;
while(l--) {
const {val, left, right} = queue.shift();
sum += val;
left && queue.push(left);
right && queue.push(right);
}
res.push(sum/len);
}
return res;
};
// 递归
var averageOfLevels = function(root) {
const resCount = [], res = [];
function defs(root, i) {
if(!root) return;
if(isNaN(res[i])) resCount[i] = res[i] = 0;
res[i] += root.val;
resCount[i]++;
root.left && defs(root.left, i + 1);
root.right && defs(root.right, i + 1);
}
defs(root, 0);
return res.map((val, i) => val / resCount[i]);
};
/**
* 515. 在每个树行中找最大值
* @param {TreeNode} root
* @return {number[]}
*/
// 迭代
const MIN_G = Number.MIN_SAFE_INTEGER;
var largestValues = function(root) {
const queue = [], res = [];
root && queue.push(root);
while(len = queue.length) {
let max = MIN_G;
while(len--) {
const {val, left, right} = queue.shift();
max = max > val ? max : val;
left && queue.push(left);
right && queue.push(right);
}
res.push(max);
}
return res;
};
// 递归
var largestValues = function(root) {
const res = [];
function defs (root, i) {
if(!root) return;
if(isNaN(res[i])) res[i] = root.val;
res[i] = res[i] > root.val ? res[i] : root.val;
root.left && defs(root.left, i + 1);
root.right && defs(root.right, i + 1);
}
defs(root, 0);
return res;
};
/**
* 429. N 叉树的层序遍历
* @param {Node|null} root
* @return {number[][]}
*/
// 迭代
var levelOrder = function(root) {
const queue = [], res = [];
root && queue.push(root);
while(len = queue.length) {
const vals = [];
while(len--) {
const {val, children} = queue.shift();
vals.push(val);
for(const e of children) {
queue.push(e);
}
}
res.push(vals);
}
return res;
};
// 递归
var levelOrder = function(root) {
const res = [];
function defs (root, i) {
if(!root) return;
if(!res[i]) res[i] = [];
res[i].push(root.val);
for(const e of root.children) {
defs(e, i + 1);
}
}
defs(root, 0);
return res;
};
/**
* 116. 填充每个节点的下一个右侧节点指针
* 117. 填充每个节点的下一个右侧节点指针 II
* @param {Node} root
* @return {Node}
*/
// 迭代
var connect = function(root) {
const queue = [];
root && queue.push(root);
while(len = queue.length) {
while(len--) {
const node1 = queue.shift(),
node2 = len ? queue[0] : null;
node1.next = node2;
node1.left && queue.push(node1.left);
node1.right && queue.push(node1.right);
}
}
return root;
};
// 递归
var connect = function(root) {
const res = [];
function defs (root, i) {
if(!root) return;
if(res[i]) res[i].next = root;
res[i] = root;
root.left && defs(root.left, i + 1);
root.right && defs(root.right, i + 1);
}
defs(root, 0);
return root;
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
看完本篇可以一起做了如下两道题目: 看完本篇可以一起做了如下两道题目:
@ -193,40 +193,6 @@ public:
}; };
``` ```
使用栈来模拟后序遍历依然可以
```C++
class Solution {
public:
int maxDepth(TreeNode* root) {
stack<TreeNode*> st;
if (root != NULL) st.push(root);
int depth = 0;
int result = 0;
while (!st.empty()) {
TreeNode* node = st.top();
if (node != NULL) {
st.pop();
st.push(node); // 中
st.push(NULL);
depth++;
if (node->right) st.push(node->right); // 右
if (node->left) st.push(node->left); // 左
} else {
st.pop();
node = st.top();
st.pop();
depth--;
}
result = result > depth ? result : depth;
}
return result;
}
};
```
## 其他语言版本 ## 其他语言版本
@ -281,9 +247,163 @@ class Solution {
Python Python
104.二叉树的最大深度
> 递归法:
```python
class Solution:
def maxDepth(self, root: TreeNode) -> int:
return self.getDepth(root)
def getDepth(self, node):
if not node:
return 0
leftDepth = self.getDepth(node.left) #左
rightDepth = self.getDepth(node.right) #右
depth = 1 + max(leftDepth, rightDepth) #中
return depth
```
> 递归法;精简代码
```python
class Solution:
def maxDepth(self, root: TreeNode) -> int:
if not root:
return 0
return 1 + max(self.maxDepth(root.left), self.maxDepth(root.right))
```
> 迭代法:
```python
import collections
class Solution:
def maxDepth(self, root: TreeNode) -> int:
if not root:
return 0
depth = 0 #记录深度
queue = collections.deque()
queue.append(root)
while queue:
size = len(queue)
depth += 1
for i in range(size):
node = queue.popleft()
if node.left:
queue.append(node.left)
if node.right:
queue.append(node.right)
return depth
```
559.N叉树的最大深度
> 递归法:
```python
class Solution:
def maxDepth(self, root: 'Node') -> int:
if not root:
return 0
depth = 0
for i in range(len(root.children)):
depth = max(depth, self.maxDepth(root.children[i]))
return depth + 1
```
> 迭代法:
```python
import collections
class Solution:
def maxDepth(self, root: 'Node') -> int:
queue = collections.deque()
if root:
queue.append(root)
depth = 0 #记录深度
while queue:
size = len(queue)
depth += 1
for i in range(size):
node = queue.popleft()
for j in range(len(node.children)):
if node.children[j]:
queue.append(node.children[j])
return depth
```
> 使用栈来模拟后序遍历依然可以
```python
class Solution:
def maxDepth(self, root: 'Node') -> int:
st = []
if root:
st.append(root)
depth = 0
result = 0
while st:
node = st.pop()
if node != None:
st.append(node) #中
st.append(None)
depth += 1
for i in range(len(node.children)): #处理孩子
if node.children[i]:
st.append(node.children[i])
else:
node = st.pop()
depth -= 1
result = max(result, depth)
return result
```
Go Go
```go
/**
* Definition for a binary tree node.
* type TreeNode struct {
* Val int
* Left *TreeNode
* Right *TreeNode
* }
*/
func max (a, b int) int {
if a > b {
return a;
}
return b;
}
// 递归
func maxDepth(root *TreeNode) int {
if root == nil {
return 0;
}
return max(maxDepth(root.Left), maxDepth(root.Right)) + 1;
}
// 遍历
func maxDepth(root *TreeNode) int {
levl := 0;
queue := make([]*TreeNode, 0);
if root != nil {
queue = append(queue, root);
}
for l := len(queue); l > 0; {
for ;l > 0;l-- {
node := queue[0];
if node.Left != nil {
queue = append(queue, node.Left);
}
if node.Right != nil {
queue = append(queue, node.Right);
}
queue = queue[1:];
}
levl++;
l = len(queue);
}
return levl;
}
```
JavaScript JavaScript
```javascript ```javascript
@ -292,6 +412,44 @@ var maxDepth = function(root) {
return 1 + Math.max(maxDepth(root.left), maxDepth(root.right)) return 1 + Math.max(maxDepth(root.left), maxDepth(root.right))
}; };
``` ```
二叉树最大深度递归遍历
```javascript
var maxDepth = function(root) {
//使用递归的方法 递归三部曲
//1. 确定递归函数的参数和返回值
const getDepth=function(node){
//2. 确定终止条件
if(node===null){
return 0;
}
//3. 确定单层逻辑
let leftDepth=getDepth(node.left);
let rightDepth=getDepth(node.right);
let depth=1+Math.max(leftDepth,rightDepth);
return depth;
}
return getDepth(root);
};
```
二叉树最大深度层级遍历
```javascript
var maxDepth = function(root) {
//使用递归的方法 递归三部曲
//1. 确定递归函数的参数和返回值
const getDepth=function(node){
//2. 确定终止条件
if(node===null){
return 0;
}
//3. 确定单层逻辑
let leftDepth=getDepth(node.left);
let rightDepth=getDepth(node.right);
let depth=1+Math.max(leftDepth,rightDepth);
return depth;
}
return getDepth(root);
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
看完本文,可以一起解决如下两道题目 看完本文,可以一起解决如下两道题目
@ -580,8 +580,10 @@ tree2 的前序遍历是[1 2 3] 后序遍历是[3 2 1]。
## 其他语言版本 ## 其他语言版本
Java Java
106.从中序与后序遍历序列构造二叉树
```java ```java
class Solution { class Solution {
public TreeNode buildTree(int[] inorder, int[] postorder) { public TreeNode buildTree(int[] inorder, int[] postorder) {
@ -617,9 +619,79 @@ class Solution {
} }
``` ```
105.从前序与中序遍历序列构造二叉树
```java
class Solution {
public TreeNode buildTree(int[] preorder, int[] inorder) {
return helper(preorder, 0, preorder.length - 1, inorder, 0, inorder.length - 1);
}
public TreeNode helper(int[] preorder, int preLeft, int preRight,
int[] inorder, int inLeft, int inRight) {
// 递归终止条件
if (inLeft > inRight || preLeft > preRight) return null;
// val 为前序遍历第一个的值,也即是根节点的值
// idx 为根据根节点的值来找中序遍历的下标
int idx = inLeft, val = preorder[preLeft];
TreeNode root = new TreeNode(val);
for (int i = inLeft; i <= inRight; i++) {
if (inorder[i] == val) {
idx = i;
break;
}
}
// 根据 idx 来递归找左右子树
root.left = helper(preorder, preLeft + 1, preLeft + (idx - inLeft),
inorder, inLeft, idx - 1);
root.right = helper(preorder, preLeft + (idx - inLeft) + 1, preRight,
inorder, idx + 1, inRight);
return root;
}
}
```
Python Python
105.从前序与中序遍历序列构造二叉树
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
//递归法
class Solution:
def buildTree(self, preorder: List[int], inorder: List[int]) -> TreeNode:
if not preorder: return None //特殊情况
root = TreeNode(preorder[0]) //新建父节点
p=inorder.index(preorder[0]) //找到父节点在中序遍历的位置(因为没有重复的元素,才可以这样找)
root.left = self.buildTree(preorder[1:p+1],inorder[:p]) //注意左节点时分割中序数组和前续数组的开闭环
root.right = self.buildTree(preorder[p+1:],inorder[p+1:]) //分割中序数组和前续数组
return root
```
106.从中序与后序遍历序列构造二叉树
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
//递归法
class Solution:
def buildTree(self, inorder: List[int], postorder: List[int]) -> TreeNode:
if not postorder: return None //特殊情况
root = TreeNode(postorder[-1]) //新建父节点
p=inorder.index(postorder[-1]) //找到父节点在中序遍历的位置*因为没有重复的元素,才可以这样找
root.left = self.buildTree(inorder[:p],postorder[:p]) //分割中序数组和后续数组
root.right = self.buildTree(inorder[p+1:],postorder[p:-1]) //注意右节点时分割中序数组和后续数组的开闭环
return root
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 构造二叉搜索树,一不小心就平衡了 > 构造二叉搜索树,一不小心就平衡了
@ -233,7 +233,27 @@ class Solution {
``` ```
Python Python
```python3
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
#递归法
class Solution:
def sortedArrayToBST(self, nums: List[int]) -> TreeNode:
def buildaTree(left,right):
if left > right: return None #左闭右闭的区间,当区间 left > right的时候就是空节点,当left = right的时候不为空
mid = left + (right - left) // 2 #保证数据不会越界
val = nums[mid]
root = TreeNode(val)
root.left = buildaTree(left,mid - 1)
root.right = buildaTree(mid + 1,right)
return root
root = buildaTree(0,len(nums) - 1) #左闭右闭区间
return root
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 求高度还是求深度,你搞懂了不? > 求高度还是求深度,你搞懂了不?
@ -142,7 +142,7 @@ int getDepth(TreeNode* node)
2. 明确终止条件 2. 明确终止条件
递归的过程中依然是遇到空节点了为终止返回0表示当前节点为根节点的高度为0 递归的过程中依然是遇到空节点了为终止返回0表示当前节点为根节点的高度为0
代码如下: 代码如下:
@ -498,6 +498,62 @@ class Solution {
Python Python
> 递归法:
```python
class Solution:
def isBalanced(self, root: TreeNode) -> bool:
return True if self.getDepth(root) != -1 else False
#返回以该节点为根节点的二叉树的高度,如果不是二叉搜索树了则返回-1
def getDepth(self, node):
if not node:
return 0
leftDepth = self.getDepth(node.left)
if leftDepth == -1: return -1 #说明左子树已经不是二叉平衡树
rightDepth = self.getDepth(node.right)
if rightDepth == -1: return -1 #说明右子树已经不是二叉平衡树
return -1 if abs(leftDepth - rightDepth)>1 else 1 + max(leftDepth, rightDepth)
```
> 迭代法:
```python
class Solution:
def isBalanced(self, root: TreeNode) -> bool:
st = []
if not root:
return True
st.append(root)
while st:
node = st.pop() #中
if abs(self.getDepth(node.left) - self.getDepth(node.right)) > 1:
return False
if node.right:
st.append(node.right) #右(空节点不入栈)
if node.left:
st.append(node.left) #左(空节点不入栈)
return True
def getDepth(self, cur):
st = []
if cur:
st.append(cur)
depth = 0
result = 0
while st:
node = st.pop()
if node:
st.append(node) #中
st.append(None)
depth += 1
if node.right: st.append(node.right) #右
if node.left: st.append(node.left) #左
else:
node = st.pop()
depth -= 1
result = max(result, depth)
return result
```
Go Go
```Go ```Go
@ -534,7 +590,34 @@ func abs(a int)int{
return a return a
} }
``` ```
JavaScript:
```javascript
var isBalanced = function(root) {
//还是用递归三部曲 + 后序遍历 左右中 当前左子树右子树高度相差大于1就返回-1
// 1. 确定递归函数参数以及返回值
const getDepth=function(node){
// 2. 确定递归函数终止条件
if(node===null){
return 0;
}
// 3. 确定单层递归逻辑
let leftDepth=getDepth(node.left);//左子树高度
if(leftDepth===-1){
return -1;
}
let rightDepth=getDepth(node.right);//右子树高度
if(rightDepth===-1){
return -1;
}
if(Math.abs(leftDepth-rightDepth)>1){
return -1;
}else{
return 1+Math.max(leftDepth,rightDepth);
}
}
return getDepth(root)===-1?false:true;
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 和求最大深度一个套路? > 和求最大深度一个套路?
@ -301,6 +301,111 @@ class Solution:
Go Go
```go
/**
* Definition for a binary tree node.
* type TreeNode struct {
* Val int
* Left *TreeNode
* Right *TreeNode
* }
*/
func min(a, b int) int {
if a < b {
return a;
}
return b;
}
// 递归
func minDepth(root *TreeNode) int {
if root == nil {
return 0;
}
if root.Left == nil && root.Right != nil {
return 1 + minDepth(root.Right);
}
if root.Right == nil && root.Left != nil {
return 1 + minDepth(root.Left);
}
return min(minDepth(root.Left), minDepth(root.Right)) + 1;
}
// 迭代
func minDepth(root *TreeNode) int {
dep := 0;
queue := make([]*TreeNode, 0);
if root != nil {
queue = append(queue, root);
}
for l := len(queue); l > 0; {
dep++;
for ; l > 0; l-- {
node := queue[0];
if node.Left == nil && node.Right == nil {
return dep;
}
if node.Left != nil {
queue = append(queue, node.Left);
}
if node.Right != nil {
queue = append(queue, node.Right);
}
queue = queue[1:];
}
l = len(queue);
}
return dep;
}
```
JavaScript:
递归法:
```javascript
/**
* @param {TreeNode} root
* @return {number}
*/
var minDepth1 = function(root) {
if(!root) return 0;
// 到叶子节点 返回 1
if(!root.left && !root.right) return 1;
// 只有右节点时 递归右节点
if(!root.left) return 1 + minDepth(root.right);、
// 只有左节点时 递归左节点
if(!root.right) return 1 + minDepth(root.left);
return Math.min(minDepth(root.left), minDepth(root.right)) + 1;
};
```
迭代法:
```javascript
/**
* @param {TreeNode} root
* @return {number}
*/
var minDepth = function(root) {
if(!root) return 0;
const queue = [root];
let dep = 0;
while(true) {
let size = queue.length;
dep++;
while(size--){
const node = queue.shift();
// 到第一个叶子节点 返回 当前深度
if(!node.left && !node.right) return dep;
node.left && queue.push(node.left);
node.right && queue.push(node.right);
}
}
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 递归函数什么时候需要返回值 > 递归函数什么时候需要返回值
@ -332,13 +332,246 @@ class Solution {
} }
} }
// LC112 简洁方法
class Solution {
public boolean hasPathSum(TreeNode root, int targetSum) {
if (root == null) return false; // 为空退出
// 叶子节点判断是否符合
if (root.left == null && root.right == null) return root.val == targetSum;
// 求两侧分支的路径和
return hasPathSum(root.left, targetSum - root.val) || hasPathSum(root.right, targetSum - root.val);
}
}
```
迭代
```java
class Solution {
public boolean hasPathSum(TreeNode root, int targetSum) {
if(root==null)return false;
Stack<TreeNode> stack1 = new Stack<>();
Stack<Integer> stack2 = new Stack<>();
stack1.push(root);stack2.push(root.val);
while(!stack1.isEmpty()){
int size = stack1.size();
for(int i=0;i<size;i++){
TreeNode node = stack1.pop();int sum=stack2.pop();
// 如果该节点是叶子节点了同时该节点的路径数值等于sum那么就返回true
if(node.left==null && node.right==null && sum==targetSum)return true;
// 右节点,压进去一个节点的时候,将该节点的路径数值也记录下来
if(node.right!=null){
stack1.push(node.right);stack2.push(sum+node.right.val);
}
// 左节点,压进去一个节点的时候,将该节点的路径数值也记录下来
if(node.left!=null){
stack1.push(node.left);stack2.push(sum+node.left.val);
}
}
}
return false;
}
}
```
0113.路径总和-ii
```java
class Solution {
public List<List<Integer>> pathSum(TreeNode root, int targetSum) {
List<List<Integer>> res = new ArrayList<>();
if (root == null) return res; // 非空判断
List<Integer> path = new LinkedList<>();
preorderDFS(root, targetSum, res, path);
return res;
}
public void preorderDFS(TreeNode root, int targetSum, List<List<Integer>> res, List<Integer> path) {
path.add(root.val);
// 遇到了叶子节点
if (root.left == null && root.right == null) {
// 找到了和为 targetSum 的路径
if (targetSum - root.val == 0) {
res.add(new ArrayList<>(path));
}
return; // 如果和不为 targetSum返回
}
if (root.left != null) {
preorderDFS(root.left, targetSum - root.val, res, path);
path.remove(path.size() - 1); // 回溯
}
if (root.right != null) {
preorderDFS(root.right, targetSum - root.val, res, path);
path.remove(path.size() - 1); // 回溯
}
}
}
``` ```
Python Python
0112.路径总和
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
// 递归法
class Solution:
def hasPathSum(self, root: TreeNode, targetSum: int) -> bool:
def isornot(root,targetSum)->bool:
if (not root.left) and (not root.right) and targetSum == 0:return True // 遇到叶子节点并且计数为0
if (not root.left) and (not root.right):return False //遇到叶子节点计数不为0
if root.left:
targetSum -= root.left.val //左节点
if isornot(root.left,targetSum):return True //递归,处理左节点
targetSum += root.left.val //回溯
if root.right:
targetSum -= root.right.val //右节点
if isornot(root.right,targetSum):return True //递归,处理右节点
targetSum += root.right.val //回溯
return False
if root == None:return False //别忘记处理空TreeNode
else:return isornot(root,targetSum-root.val)
```
0113.路径总和-ii
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
//递归法
class Solution:
def pathSum(self, root: TreeNode, targetSum: int) -> List[List[int]]:
path=[]
res=[]
def pathes(root,targetSum):
if (not root.left) and (not root.right) and targetSum == 0: // 遇到叶子节点并且计数为0
res.append(path[:]) //找到一种路径记录到res中注意必须是path[:]而不是path
return
if (not root.left) and (not root.right):return // 遇到叶子节点直接返回
if root.left: //左
targetSum -= root.left.val
path.append(root.left.val) //递归前记录节点
pathes(root.left,targetSum) //递归
targetSum += root.left.val //回溯
path.pop() //回溯
if root.right: //右
targetSum -= root.right.val
path.append(root.right.val) //递归前记录节点
pathes(root.right,targetSum) //递归
targetSum += root.right.val //回溯
path.pop() //回溯
return
if root == None:return [] //处理空TreeNode
else:
path.append(root.val) //首先处理根节点
pathes(root,targetSum-root.val)
return res
```
Go Go
> 112. 路径总和
```go
//递归法
/**
* Definition for a binary tree node.
* type TreeNode struct {
* Val int
* Left *TreeNode
* Right *TreeNode
* }
*/
func hasPathSum(root *TreeNode, targetSum int) bool {
var flage bool //找没找到的标志
if root==nil{
return flage
}
pathSum(root,0,targetSum,&flage)
return flage
}
func pathSum(root *TreeNode, sum int,targetSum int,flage *bool){
sum+=root.Val
if root.Left==nil&&root.Right==nil&&sum==targetSum{
*flage=true
return
}
if root.Left!=nil&&!(*flage){//左节点不为空且还没找到
pathSum(root.Left,sum,targetSum,flage)
}
if root.Right!=nil&&!(*flage){//右节点不为空且没找到
pathSum(root.Right,sum,targetSum,flage)
}
}
```
> 113 递归法
```go
/**
* Definition for a binary tree node.
* type TreeNode struct {
* Val int
* Left *TreeNode
* Right *TreeNode
* }
*/
func pathSum(root *TreeNode, targetSum int) [][]int {
var result [][]int//最终结果
if root==nil{
return result
}
var sumNodes []int//经过路径的节点集合
hasPathSum(root,&sumNodes,targetSum,&result)
return result
}
func hasPathSum(root *TreeNode,sumNodes *[]int,targetSum int,result *[][]int){
*sumNodes=append(*sumNodes,root.Val)
if root.Left==nil&&root.Right==nil{//叶子节点
fmt.Println(*sumNodes)
var sum int
var number int
for k,v:=range *sumNodes{//求该路径节点的和
sum+=v
number=k
}
tempNodes:=make([]int,number+1)//新的nodes接受指针里的值防止最终指针里的值发生变动导致最后的结果都是最后一个sumNodes的值
for k,v:=range *sumNodes{
tempNodes[k]=v
}
if sum==targetSum{
*result=append(*result,tempNodes)
}
}
if root.Left!=nil{
hasPathSum(root.Left,sumNodes,targetSum,result)
*sumNodes=(*sumNodes)[:len(*sumNodes)-1]//回溯
}
if root.Right!=nil{
hasPathSum(root.Right,sumNodes,targetSum,result)
*sumNodes=(*sumNodes)[:len(*sumNodes)-1]//回溯
}
}
```
JavaScript JavaScript
0112.路径总和 0112.路径总和
@ -407,6 +640,62 @@ let pathSum = function (root, targetSum) {
}; };
``` ```
0112 路径总和
```javascript
var hasPathSum = function(root, targetSum) {
//递归方法
// 1. 确定函数参数
const traversal = function(node,count){
// 2. 确定终止条件
if(node.left===null&&node.right===null&&count===0){
return true;
}
if(node.left===null&&node.right===null){
return false;
}
//3. 单层递归逻辑
if(node.left){
if(traversal(node.left,count-node.left.val)){
return true;
}
}
if(node.right){
if(traversal(node.right,count-node.right.val)){
return true;
}
}
return false;
}
if(root===null){
return false;
}
return traversal(root,targetSum-root.val);
};
```
113 路径总和
```javascript
var pathSum = function(root, targetSum) {
//递归方法
let resPath = [],curPath = [];
// 1. 确定递归函数参数
const travelTree = function(node,count){
curPath.push(node.val);
count-=node.val;
if(node.left===null&&node.right===null&&count===0){
resPath.push([...curPath]);
}
node.left&&travelTree(node.left,count);
node.right&&travelTree(node.right,count);
let cur = curPath.pop();
count-=cur;
}
if(root===null){
return resPath;
}
travelTree(root,targetSum);
return resPath;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 115.不同的子序列 ## 115.不同的子序列
@ -16,7 +16,7 @@
题目数据保证答案符合 32 位带符号整数范围。 题目数据保证答案符合 32 位带符号整数范围。
![115.不同的子序列示例](https://code-thinking.cdn.bcebos.com/pics/115.%E4%B8%8D%E5%90%8C%E7%9A%84%E5%AD%90%E5%BA%8F%E5%88%97%E7%A4%BA%E4%BE%8B.jpg) ![115.不同的子序列示例](https://code-thinking.cdn.bcebos.com/pics/115.不同的子序列示例.jpg)
提示: 提示:
@ -148,7 +148,22 @@ Java
Python Python
```python
class Solution:
def numDistinct(self, s: str, t: str) -> int:
dp = [[0] * (len(t)+1) for _ in range(len(s)+1)]
for i in range(len(s)):
dp[i][0] = 1
for j in range(1, len(t)):
dp[0][j] = 0
for i in range(1, len(s)+1):
for j in range(1, len(t)+1):
if s[i-1] == t[j-1]:
dp[i][j] = dp[i-1][j-1] + dp[i-1][j]
else:
dp[i][j] = dp[i-1][j]
return dp[-1][-1]
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 121. 买卖股票的最佳时机 ## 121. 买卖股票的最佳时机
@ -33,7 +33,7 @@
这道题目最直观的想法,就是暴力,找最优间距了。 这道题目最直观的想法,就是暴力,找最优间距了。
``` ```C++
class Solution { class Solution {
public: public:
int maxProfit(vector<int>& prices) { int maxProfit(vector<int>& prices) {
@ -196,14 +196,122 @@ public:
## 其他语言版本 ## 其他语言版本
Java Java
```java
// 贪心思路
class Solution {
public int maxProfit(int[] prices) {
int minprice = Integer.MAX_VALUE;
int maxprofit = 0;
for (int i = 0; i < prices.length; i++) {
if (prices[i] < minprice) {
minprice = prices[i];
} else if (prices[i] - minprice > maxprofit) {
maxprofit = prices[i] - minprice;
}
}
return maxprofit;
}
}
```
``` java
class Solution { // 动态规划解法
public int maxProfit(int[] prices) {
// 可交易次数
int k = 1;
// [天数][交易次数][是否持有股票]
int[][][] dp = new int[prices.length][k + 1][2];
// bad case
dp[0][0][0] = 0;
dp[0][0][1] = Integer.MIN_VALUE;
dp[0][1][0] = Integer.MIN_VALUE;
dp[0][1][1] = -prices[0];
for (int i = 1; i < prices.length; i++) {
for (int j = k; j >= 1; j--) {
// dp公式
dp[i][j][0] = Math.max(dp[i - 1][j][0], dp[i - 1][j][1] + prices[i]);
dp[i][j][1] = Math.max(dp[i - 1][j][1], dp[i - 1][j - 1][0] - prices[i]);
}
}
return dp[prices.length - 1][k][0] > 0 ? dp[prices.length - 1][k][0] : 0;
}
}
```
Python Python
> 贪心法:
```python
class Solution:
def maxProfit(self, prices: List[int]) -> int:
low = float("inf")
result = 0
for i in range(len(prices)):
low = min(low, prices[i]) #取最左最小价格
result = max(result, prices[i] - low) #直接取最大区间利润
return result
```
> 动态规划:版本一
```python
class Solution:
def maxProfit(self, prices: List[int]) -> int:
length = len(prices)
if len == 0:
return 0
dp = [[0] * 2 for _ in range(length)]
dp[0][0] = -prices[0]
dp[0][1] = 0
for i in range(1, length):
dp[i][0] = max(dp[i-1][0], -prices[i])
dp[i][1] = max(dp[i-1][1], prices[i] + dp[i-1][0])
return dp[-1][1]
```
> 动态规划:版本二
```python
class Solution:
def maxProfit(self, prices: List[int]) -> int:
length = len(prices)
dp = [[0] * 2 for _ in range(2)] #注意这里只开辟了一个2 * 2大小的二维数组
dp[0][0] = -prices[0]
dp[0][1] = 0
for i in range(1, length):
dp[i % 2][0] = max(dp[(i-1) % 2][0], -prices[i])
dp[i % 2][1] = max(dp[(i-1) % 2][1], prices[i] + dp[(i-1) % 2][0])
return dp[(length-1) % 2][1]
```
Go Go
```Go
func maxProfit(prices []int) int {
length:=len(prices)
if length==0{return 0}
dp:=make([][]int,length)
for i:=0;i<length;i++{
dp[i]=make([]int,2)
}
dp[0][0]=-prices[0]
dp[0][1]=0
for i:=1;i<length;i++{
dp[i][0]=max(dp[i-1][0],-prices[i])
dp[i][1]=max(dp[i-1][1],dp[i-1][0]+prices[i])
}
return dp[length-1][1]
}
func max(a,b int)int {
if a>b{
return a
}
return b
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 122.买卖股票的最佳时机II ## 122.买卖股票的最佳时机II
@ -133,9 +133,10 @@ public:
## 其他语言版本 ## 其他语言版本
Java Java
```java ```java
// 贪心思路
class Solution { class Solution {
public int maxProfit(int[] prices) { public int maxProfit(int[] prices) {
int sum = 0; int sum = 0;
@ -153,6 +154,29 @@ class Solution {
} }
``` ```
```java
class Solution { // 动态规划
public int maxProfit(int[] prices) {
// [天数][是否持有股票]
int[][] dp = new int[prices.length][2];
// bad case
dp[0][0] = 0;
dp[0][1] = -prices[0];
for (int i = 1; i < prices.length; i++) {
// dp公式
dp[i][0] = Math.max(dp[i - 1][0], dp[i - 1][1] + prices[i]);
dp[i][1] = Math.max(dp[i - 1][1], dp[i - 1][0] - prices[i]);
}
return dp[prices.length - 1][0];
}
}
```
Python Python
```python ```python
class Solution: class Solution:
@ -166,7 +190,17 @@ class Solution:
Go Go
Javascript:
```Javascript
// 贪心
var maxProfit = function(prices) {
let result = 0
for(let i = 1; i < prices.length; i++) {
result += Math.max(prices[i] - prices[i - 1], 0)
}
return result
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 122.买卖股票的最佳时机II ## 122.买卖股票的最佳时机II
@ -133,10 +133,71 @@ public:
Java Java
```java
// 动态规划
class Solution
// 实现1二维数组存储
// 可以将每天持有与否的情况分别用 dp[i][0] 和 dp[i][1] 来进行存储
// 时间复杂度O(n)空间复杂度O(n)
public int maxProfit(int[] prices) {
int n = prices.length;
int[][] dp = new int[n][2]; // 创建二维数组存储状态
dp[0][0] = 0; // 初始状态
dp[0][1] = -prices[0];
for (int i = 1; i < n; ++i) {
dp[i][0] = Math.max(dp[i - 1][0], dp[i - 1][1] + prices[i]); // 第 i 天,没有股票
dp[i][1] = Math.max(dp[i - 1][1], dp[i - 1][0] - prices[i]); // 第 i 天,持有股票
}
return dp[n - 1][0]; // 卖出股票收益高于持有股票收益,因此取[0]
}
// 实现2变量存储
// 第一种方法需要用二维数组存储,有空间开销,其实关心的仅仅是前一天的状态,不关注更多的历史信息
// 因此,可以仅保存前一天的信息存入 dp0、dp1 这 2 个变量即可
// 时间复杂度O(n)空间复杂度O(1)
public int maxProfit(int[] prices) {
int n = prices.length;
int dp0 = 0, dp1 = -prices[0]; // 定义变量,存储初始状态
for (int i = 1; i < n; ++i) {
int newDp0 = Math.max(dp0, dp1 + prices[i]); // 第 i 天,没有股票
int newDp1 = Math.max(dp1, dp0 - prices[i]); // 第 i 天,持有股票
dp0 = newDp0;
dp1 = newDp1;
}
return dp0;
}
}
```
Python Python
> 版本一:
```python
class Solution:
def maxProfit(self, prices: List[int]) -> int:
length = len(prices)
dp = [[0] * 2 for _ in range(length)]
dp[0][0] = -prices[0]
dp[0][1] = 0
for i in range(1, length):
dp[i][0] = max(dp[i-1][0], dp[i-1][1] - prices[i]) #注意这里是和121. 买卖股票的最佳时机唯一不同的地方
dp[i][1] = max(dp[i-1][1], dp[i-1][0] + prices[i])
return dp[-1][1]
```
> 版本二:
```python
class Solution:
def maxProfit(self, prices: List[int]) -> int:
length = len(prices)
dp = [[0] * 2 for _ in range(2)] #注意这里只开辟了一个2 * 2大小的二维数组
dp[0][0] = -prices[0]
dp[0][1] = 0
for i in range(1, length):
dp[i % 2][0] = max(dp[(i-1) % 2][0], dp[(i-1) % 2][1] - prices[i])
dp[i % 2][1] = max(dp[(i-1) % 2][1], dp[(i-1) % 2][0] + prices[i])
return dp[(length-1) % 2][1]
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 123.买卖股票的最佳时机III ## 123.买卖股票的最佳时机III
@ -101,9 +101,9 @@ dp[i][4] = max(dp[i - 1][4], dp[i - 1][3] + prices[i]);
所以dp[0][2] = 0; 所以dp[0][2] = 0;
第0天第二次买入操作初始值应该是多少呢 第0天第二次买入操作初始值应该是多少呢应该不少同学疑惑,第一次还没买入呢,怎么初始化第二次买入呢?
不用管第几次,现在手头上没有现金,只要买入,现金就做相应的减少。 第二次买入依赖于第一次卖出的状态其实相当于第0天第一次买入了第一次卖出了然后在买入一次第二次买入那么现在手头上没有现金,只要买入,现金就做相应的减少。
所以第二次买入操作初始化为dp[0][3] = -prices[0]; 所以第二次买入操作初始化为dp[0][3] = -prices[0];
@ -190,12 +190,79 @@ dp[1] = max(dp[1], dp[0] - prices[i]); 如果dp[1]取dp[1],即保持买入股
## 其他语言版本 ## 其他语言版本
Java Java
```java
class Solution { // 动态规划
public int maxProfit(int[] prices) {
// 可交易次数
int k = 2;
// [天数][交易次数][是否持有股票]
int[][][] dp = new int[prices.length][k + 1][2];
// badcase
dp[0][0][0] = 0;
dp[0][0][1] = Integer.MIN_VALUE;
dp[0][1][0] = 0;
dp[0][1][1] = -prices[0];
dp[0][2][0] = 0;
dp[0][2][1] = Integer.MIN_VALUE;
for (int i = 1; i < prices.length; i++) {
for (int j = 2; j >= 1; j--) {
// dp公式
dp[i][j][0] = Math.max(dp[i - 1][j][0], dp[i - 1][j][1] + prices[i]);
dp[i][j][1] = Math.max(dp[i - 1][j][1], dp[i - 1][j - 1][0] - prices[i]);
}
}
int res = 0;
for (int i = 1; i < 3; i++) {
res = Math.max(res, dp[prices.length - 1][i][0]);
}
return res;
}
}
```
Python Python
> 版本一:
```python
class Solution:
def maxProfit(self, prices: List[int]) -> int:
if len(prices) == 0:
return 0
dp = [[0] * 5 for _ in range(len(prices))]
dp[0][1] = -prices[0]
dp[0][3] = -prices[0]
for i in range(1, len(prices)):
dp[i][0] = dp[i-1][0]
dp[i][1] = max(dp[i-1][1], dp[i-1][0] - prices[i])
dp[i][2] = max(dp[i-1][2], dp[i-1][1] + prices[i])
dp[i][3] = max(dp[i-1][3], dp[i-1][2] - prices[i])
dp[i][4] = max(dp[i-1][4], dp[i-1][3] + prices[i])
return dp[-1][4]
```
> 版本二:
```python
class Solution:
def maxProfit(self, prices: List[int]) -> int:
if len(prices) == 0:
return 0
dp = [0] * 5
dp[1] = -prices[0]
dp[3] = -prices[0]
for i in range(1, len(prices)):
dp[1] = max(dp[1], dp[0] - prices[i])
dp[2] = max(dp[2], dp[1] + prices[i])
dp[3] = max(dp[3], dp[2] - prices[i])
dp[4] = max(dp[4], dp[3] + prices[i])
return dp[4]
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 切割问题其实是一种组合问题! > 切割问题其实是一种组合问题!
@ -292,11 +292,59 @@ class Solution {
``` ```
Python Python
```py
class Solution:
def partition(self, s: str) -> List[List[str]]:
res = []
path = [] #放已经回文的子串
def backtrack(s,startIndex):
if startIndex >= len(s): #如果起始位置已经大于s的大小,说明已经找到了一组分割方案了
return res.append(path[:])
for i in range(startIndex,len(s)):
p = s[startIndex:i+1] #获取[startIndex,i+1]在s中的子串
if p == p[::-1]: path.append(p) #是回文子串
else: continue #不是回文,跳过
backtrack(s,i+1) #寻找i+1为起始位置的子串
path.pop() #回溯过程弹出本次已经填在path的子串
backtrack(s,0)
return res
```
Go Go
javaScript
```js
/**
* @param {string} s
* @return {string[][]}
*/
const isPalindrome = (s, l, r) => {
for (let i = l, j = r; i < j; i++, j--) {
if(s[i] !== s[j]) return false;
}
return true;
}
var partition = function(s) {
const res = [], path = [], len = s.length;
backtracking(0);
return res;
function backtracking(i) {
if(i >= len) {
res.push(Array.from(path));
return;
}
for(let j = i; j < len; j++) {
if(!isPalindrome(s, i, j)) continue;
path.push(s.substr(i, j - i + 1));
backtracking(j + 1);
path.pop();
}
}
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 134. 加油站 ## 134. 加油站
@ -223,11 +223,46 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def canCompleteCircuit(self, gas: List[int], cost: List[int]) -> int:
start = 0
curSum = 0
totalSum = 0
for i in range(len(gas)):
curSum += gas[i] - cost[i]
totalSum += gas[i] - cost[i]
if curSum < 0:
curSum = 0
start = i + 1
if totalSum < 0: return -1
return start
```
Go Go
Javascript:
```Javascript
var canCompleteCircuit = function(gas, cost) {
const gasLen = gas.length
let start = 0
let curSum = 0
let totalSum = 0
for(let i = 0; i < gasLen; i++) {
curSum += gas[i] - cost[i]
totalSum += gas[i] - cost[i]
if(curSum < 0) {
curSum = 0
start = i + 1
}
}
if(totalSum < 0) return -1
return start
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 135. 分发糖果 ## 135. 分发糖果
@ -161,11 +161,45 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def candy(self, ratings: List[int]) -> int:
candyVec = [1] * len(ratings)
for i in range(1, len(ratings)):
if ratings[i] > ratings[i - 1]:
candyVec[i] = candyVec[i - 1] + 1
for j in range(len(ratings) - 2, -1, -1):
if ratings[j] > ratings[j + 1]:
candyVec[j] = max(candyVec[j], candyVec[j + 1] + 1)
return sum(candyVec)
```
Go Go
Javascript:
```Javascript
var candy = function(ratings) {
let candys = new Array(ratings.length).fill(1)
for(let i = 1; i < ratings.length; i++) {
if(ratings[i] > ratings[i - 1]) {
candys[i] = candys[i - 1] + 1
}
}
for(let i = ratings.length - 2; i >= 0; i--) {
if(ratings[i] > ratings[i + 1]) {
candys[i] = Math.max(candys[i], candys[i + 1] + 1)
}
}
let count = candys.reduce((a, b) => {
return a + b
})
return count
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 动态规划:单词拆分 # 动态规划:单词拆分
## 139.单词拆分 ## 139.单词拆分
@ -252,9 +252,44 @@ class Solution {
Python Python
```python3
class Solution:
def wordBreak(self, s: str, wordDict: List[str]) -> bool:
'''排列'''
dp = [False]*(len(s) + 1)
dp[0] = True
# 遍历背包
for j in range(1, len(s) + 1):
# 遍历单词
for word in wordDict:
if j >= len(word):
dp[j] = dp[j] or (dp[j - len(word)] and word == s[j - len(word):j])
return dp[len(s)]
```
Go Go
```Go
func wordBreak(s string,wordDict []string) bool {
wordDictSet:=make(map[string]bool)
for _,w:=range wordDict{
wordDictSet[w]=true
}
dp:=make([]bool,len(s)+1)
dp[0]=true
for i:=1;i<=len(s);i++{
for j:=0;j<i;j++{
if dp[j]&& wordDictSet[s[j:i]]{
dp[i]=true
break
}
}
}
return dp[len(s)]
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -234,6 +234,67 @@ class Solution:
``` ```
Go Go
```go
func detectCycle(head *ListNode) *ListNode {
slow, fast := head, head
for fast != nil && fast.Next != nil {
slow = slow.Next
fast = fast.Next.Next
if slow == fast {
for slow != head {
slow = slow.Next
head = head.Next
}
return head
}
}
return nil
}
```
javaScript
```js
// 两种循环实现方式
/**
* @param {ListNode} head
* @return {ListNode}
*/
// 先判断是否是环形链表
var detectCycle = function(head) {
if(!head || !head.next) return null;
let slow =head.next, fast = head.next.next;
while(fast && fast.next && fast!== slow) {
slow = slow.next;
fast = fast.next.next;
}
if(!fast || !fast.next ) return null;
slow = head;
while (fast !== slow) {
slow = slow.next;
fast = fast.next;
}
return slow;
};
var detectCycle = function(head) {
if(!head || !head.next) return null;
let slow =head.next, fast = head.next.next;
while(fast && fast.next) {
slow = slow.next;
fast = fast.next.next;
if(fast == slow) {
slow = head;
while (fast !== slow) {
slow = slow.next;
fast = fast.next;
}
return slow;
}
}
return null;
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -170,8 +170,75 @@ public class EvalRPN {
} }
``` ```
Go:
```Go
func evalRPN(tokens []string) int {
stack := []int{}
for _, token := range tokens {
val, err := strconv.Atoi(token)
if err == nil {
stack = append(stack, val)
} else {
num1, num2 := stack[len(stack)-2], stack[(len(stack))-1]
stack = stack[:len(stack)-2]
switch token {
case "+":
stack = append(stack, num1+num2)
case "-":
stack = append(stack, num1-num2)
case "*":
stack = append(stack, num1*num2)
case "/":
stack = append(stack, num1/num2)
}
}
}
return stack[0]
}
```
javaScript:
```js
/**
* @param {string[]} tokens
* @return {number}
*/
var evalRPN = function(tokens) {
const s = new Map([
["+", (a, b) => a * 1 + b * 1],
["-", (a, b) => b - a],
["*", (a, b) => b * a],
["/", (a, b) => (b / a) | 0]
]);
const stack = [];
for (const i of tokens) {
if(!s.has(i)) {
stack.push(i);
continue;
}
stack.push(s.get(i)(stack.pop(),stack.pop()))
}
return stack.pop();
};
```
python3
```python
def evalRPN(tokens) -> int:
stack = list()
for i in range(len(tokens)):
if tokens[i] not in ["+", "-", "*", "/"]:
stack.append(tokens[i])
else:
tmp1 = stack.pop()
tmp2 = stack.pop()
res = eval(tmp2+tokens[i]+tmp1)
stack.append(str(int(res)))
return stack[-1]
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -183,7 +183,7 @@ public:
int end = 0; // 反转的单词在字符串里终止位置 int end = 0; // 反转的单词在字符串里终止位置
bool entry = false; // 标记枚举字符串的过程中是否已经进入了单词区间 bool entry = false; // 标记枚举字符串的过程中是否已经进入了单词区间
for (int i = 0; i < s.size(); i++) { // 开始反转单词 for (int i = 0; i < s.size(); i++) { // 开始反转单词
if ((!entry) || (s[i] != ' ' && s[i - 1] == ' ')) { if (!entry) {
start = i; // 确定单词起始位置 start = i; // 确定单词起始位置
entry = true; // 进入单词区间 entry = true; // 进入单词区间
} }
@ -318,9 +318,61 @@ class Solution {
Python Python
Go Go
```go
import (
"fmt"
)
func reverseWords(s string) string {
//1.使用双指针删除冗余的空格
slowIndex, fastIndex := 0, 0
b := []byte(s)
//删除头部冗余空格
for len(b) > 0 && fastIndex < len(b) && b[fastIndex] == ' ' {
fastIndex++
}
//删除单词间冗余空格
for ; fastIndex < len(b); fastIndex++ {
if fastIndex-1 > 0 && b[fastIndex-1] == b[fastIndex] && b[fastIndex] == ' ' {
continue
}
b[slowIndex] = b[fastIndex]
slowIndex++
}
//删除尾部冗余空格
if slowIndex-1 > 0 && b[slowIndex-1] == ' ' {
b = b[:slowIndex-1]
} else {
b = b[:slowIndex]
}
//2.反转整个字符串
reverse(&b, 0, len(b)-1)
//3.反转单个单词 i单词开始位置j单词结束位置
i := 0
for i < len(b) {
j := i
for ; j < len(b) && b[j] != ' '; j++ {
}
reverse(&b, i, j-1)
i = j
i++
}
return string(b)
}
func reverse(b *[]byte, left, right int) {
for left < right {
(*b)[left], (*b)[right] = (*b)[right], (*b)[left]
left++
right--
}
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 188.买卖股票的最佳时机IV ## 188.买卖股票的最佳时机IV
@ -25,7 +25,7 @@
输入k = 2, prices = [3,2,6,5,0,3] 输入k = 2, prices = [3,2,6,5,0,3]
输出7 输出7
解释:在第 2 天 (股票价格 = 2) 的时候买入,在第 3 天 (股票价格 = 6) 的时候卖出, 这笔交易所能获得利润 = 6-2 = 4。随后在第 5 天 (股票价格 = 0) 的时候买入,在第 6 天 (股票价格 = 3) 的时候卖出, 这笔交易所能获得利润 = 3-0 = 3 。 解释:在第 2 天 (股票价格 = 2) 的时候买入,在第 3 天 (股票价格 = 6) 的时候卖出, 这笔交易所能获得利润 = 6-2 = 4。随后在第 5 天 (股票价格 = 0) 的时候买入,在第 6 天 (股票价格 = 3) 的时候卖出, 这笔交易所能获得利润 = 3-0 = 3 。
 
提示: 提示:
@ -167,12 +167,65 @@ public:
## 其他语言版本 ## 其他语言版本
Java Java
```java
class Solution { //动态规划
public int maxProfit(int k, int[] prices) {
if (prices == null || prices.length < 2 || k == 0) {
return 0;
}
// [天数][交易次数][是否持有股票]
int[][][] dp = new int[prices.length][k + 1][2];
// bad case
dp[0][0][0] = 0;
dp[0][0][1] = Integer.MIN_VALUE;
dp[0][1][0] = 0;
dp[0][1][1] = -prices[0];
// dp[0][j][0] 都均为0
// dp[0][j][1] 异常值都取Integer.MIN_VALUE;
for (int i = 2; i < k + 1; i++) {
dp[0][i][0] = 0;
dp[0][i][1] = Integer.MIN_VALUE;
}
for (int i = 1; i < prices.length; i++) {
for (int j = k; j >= 1; j--) {
// dp公式
dp[i][j][0] = Math.max(dp[i - 1][j][0], dp[i - 1][j][1] + prices[i]);
dp[i][j][1] = Math.max(dp[i - 1][j][1], dp[i - 1][j - 1][0] - prices[i]);
}
}
int res = 0;
for (int i = 1; i < k + 1; i++) {
res = Math.max(res, dp[prices.length - 1][i][0]);
}
return res;
}
}
```
Python Python
```python
class Solution:
def maxProfit(self, k: int, prices: List[int]) -> int:
if len(prices) == 0:
return 0
dp = [[0] * (2*k+1) for _ in range(len(prices))]
for j in range(1, 2*k, 2):
dp[0][j] = -prices[0]
for i in range(1, len(prices)):
for j in range(0, 2*k-1, 2):
dp[i][j+1] = max(dp[i-1][j+1], dp[i-1][j] - prices[i])
dp[i][j+2] = max(dp[i-1][j+2], dp[i-1][j+1] + prices[i])
return dp[-1][2*k]
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 198.打家劫舍 ## 198.打家劫舍
@ -111,10 +111,40 @@ public:
Java Java
```Java
// 动态规划
class Solution {
public int rob(int[] nums) {
if (nums == null || nums.length == 0) return 0;
if (nums.length == 1) return nums[0];
int[] dp = new int[nums.length];
dp[0] = nums[0];
dp[1] = Math.max(dp[0], nums[1]);
for (int i = 2; i < nums.length; i++) {
dp[i] = Math.max(dp[i - 1], dp[i - 2] + nums[i]);
}
return dp[nums.length - 1];
}
}
```
Python Python
```python
class Solution:
def rob(self, nums: List[int]) -> int:
if len(nums) == 0:
return 0
if len(nums) == 1:
return nums[0]
dp = [0] * len(nums)
dp[0] = nums[0]
dp[1] = max(nums[0], nums[1])
for i in range(2, len(nums)):
dp[i] = max(dp[i-2]+nums[i], dp[i-1])
return dp[-1]
```
Go Go
```Go ```Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -36,7 +36,7 @@ https://leetcode-cn.com/problems/happy-number/
题目中说了会 **无限循环**,那么也就是说**求和的过程中sum会重复出现这对解题很重要** 题目中说了会 **无限循环**,那么也就是说**求和的过程中sum会重复出现这对解题很重要**
正如:[关于哈希表,你该了解这些!](https://mp.weixin.qq.com/s/g8N6WmoQmsCUw3_BaWxHZA)中所说,**当我们遇到了要快速判断一个元素是否出现集合里的时候,就要考虑哈希法了。** 正如:[关于哈希表,你该了解这些!](https://mp.weixin.qq.com/s/RSUANESA_tkhKhYe3ZR8Jg)中所说,**当我们遇到了要快速判断一个元素是否出现集合里的时候,就要考虑哈希法了。**
所以这道题目使用哈希法来判断这个sum是否重复出现如果重复了就是return false 否则一直找到sum为1为止。 所以这道题目使用哈希法来判断这个sum是否重复出现如果重复了就是return false 否则一直找到sum为1为止。
@ -80,7 +80,7 @@ public:
## 其他语言版本 # 其他语言版本
Java Java
@ -108,10 +108,84 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def isHappy(self, n: int) -> bool:
set_ = set()
while 1:
sum_ = self.getSum(n)
if sum_ == 1:
return True
#如果这个sum曾经出现过说明已经陷入了无限循环了立刻return false
if sum_ in set_:
return False
else:
set_.add(sum_)
n = sum_
#取数值各个位上的单数之和
def getSum(self, n):
sum_ = 0
while n > 0:
sum_ += (n%10) * (n%10)
n //= 10
return sum_
```
Go Go
```go
func isHappy(n int) bool {
m := make(map[int]bool)
for n != 1 && !m[n] {
n, m[n] = getSum(n), true
}
return n == 1
}
func getSum(n int) int {
sum := 0
for n > 0 {
sum += (n % 10) * (n % 10)
n = n / 10
}
return sum
}
```
javaScript:
```js
function getN(n) {
if (n == 1 || n == 0) return n;
let res = 0;
while (n) {
res += (n % 10) * (n % 10);
n = parseInt(n / 10);
}
return res;
}
var isHappy = function(n) {
const sumSet = new Set();
while (n != 1 && !sumSet.has(n)) {
sumSet.add(n);
n = getN(n);
}
return n == 1;
};
// 使用环形链表的思想 说明出现闭环 退出循环
var isHappy = function(n) {
if (getN(n) == 1) return true;
let a = getN(n), b = getN(getN(n));
// 如果 a === b
while (b !== 1 && getN(b) !== 1 && a !== b) {
a = getN(a);
b = getN(getN(b));
}
return b === 1 || getN(b) === 1 ;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 链表操作中,可以使用原链表来直接进行删除操作,也可以设置一个虚拟头结点在进行删除操作,接下来看一看哪种方式更方便。 > 链表操作中,可以使用原链表来直接进行删除操作,也可以设置一个虚拟头结点在进行删除操作,接下来看一看哪种方式更方便。
@ -15,7 +15,18 @@ https://leetcode-cn.com/problems/remove-linked-list-elements/
题意:删除链表中等于给定值 val 的所有节点。 题意:删除链表中等于给定值 val 的所有节点。
![203题目示例](https://img-blog.csdnimg.cn/20200814104441179.png) 示例 1
输入head = [1,2,6,3,4,5,6], val = 6
输出:[1,2,3,4,5]
示例 2
输入head = [], val = 1
输出:[]
示例 3
输入head = [7,7,7,7], val = 7
输出:[]
# 思路 # 思路
@ -197,10 +208,71 @@ public ListNode removeElements(ListNode head, int val) {
``` ```
Python Python
```python
# Definition for singly-linked list.
# class ListNode:
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution:
def removeElements(self, head: ListNode, val: int) -> ListNode:
dummy_head = ListNode(next=head) #添加一个虚拟节点
cur = dummy_head
while(cur.next!=None):
if(cur.next.val == val):
cur.next = cur.next.next #删除cur.next节点
else:
cur = cur.next
return dummy_head.next
```
Go Go
```go
/**
* Definition for singly-linked list.
* type ListNode struct {
* Val int
* Next *ListNode
* }
*/
func removeElements(head *ListNode, val int) *ListNode {
dummyHead := &ListNode{}
dummyHead.Next = head
cur := dummyHead
for cur != nil && cur.Next != nil {
if cur.Next.Val == val {
cur.Next = cur.Next.Next
} else {
cur = cur.Next
}
}
return dummyHead.Next
}
```
javaScript:
```js
/**
* @param {ListNode} head
* @param {number} val
* @return {ListNode}
*/
var removeElements = function(head, val) {
const ret = new ListNode(0, head);
let cur = ret;
while(cur.next) {
if(cur.next.val === val) {
cur.next = cur.next.next;
continue;
}
cur = cur.next;
}
return ret.next;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 反转链表的写法很简单,一些同学甚至可以背下来但过一阵就忘了该咋写,主要是因为没有理解真正的反转过程。 > 反转链表的写法很简单,一些同学甚至可以背下来但过一阵就忘了该咋写,主要是因为没有理解真正的反转过程。
@ -143,10 +143,112 @@ class Solution {
``` ```
Python Python
```python
#双指针
# Definition for singly-linked list.
# class ListNode:
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution:
def reverseList(self, head: ListNode) -> ListNode:
cur = head
pre = None
while(cur!=None):
temp = cur.next # 保存一下 cur的下一个节点因为接下来要改变cur->next
cur.next = pre #反转
#更新pre、cur指针
pre = cur
cur = temp
return pre
```
Go Go
```go
//双指针
func reverseList(head *ListNode) *ListNode {
var pre *ListNode
cur := head
for cur != nil {
next := cur.Next
cur.Next = pre
pre = cur
cur = next
}
return pre
}
//递归
func reverseList(head *ListNode) *ListNode {
return help(nil, head)
}
func help(pre, head *ListNode)*ListNode{
if head == nil {
return pre
}
next := head.Next
head.Next = pre
return help(head, next)
}
```
javaScript:
```js
/**
* @param {ListNode} head
* @return {ListNode}
*/
// 双指针:
var reverseList = function(head) {
if(!head || !head.next) return head;
let temp = null, pre = null, cur = head;
while(cur) {
temp = cur.next;
cur.next = pre;
pre = cur;
cur = temp;
}
// temp = cur = null;
return pre;
};
// 递归:
var reverse = function(pre, head) {
if(!head) return pre;
const temp = head.next;
head.next = pre;
pre = head
return reverse(pre, temp);
}
var reverseList = function(head) {
return reverse(null, head);
};
// 递归2
var reverse = function(head) {
if(!head || !head.next) return head;
// 从后往前翻
const pre = reverse(head.next);
head.next = pre.next;
pre.next = head;
return head;
}
var reverseList = function(head) {
let cur = head;
while(cur && cur.next) {
cur = cur.next;
}
reverse(head);
return cur;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 209.长度最小的子数组 ## 209.长度最小的子数组
@ -116,26 +116,6 @@ public:
不要以为for里放一个while就以为是$O(n^2)$啊, 主要是看每一个元素被操作的次数每个元素在滑动窗后进来操作一次出去操作一次每个元素都是被被操作两次所以时间复杂度是2 * n 也就是$O(n)$。 不要以为for里放一个while就以为是$O(n^2)$啊, 主要是看每一个元素被操作的次数每个元素在滑动窗后进来操作一次出去操作一次每个元素都是被被操作两次所以时间复杂度是2 * n 也就是$O(n)$。
## 其他语言补充
python
```python
class Solution:
def minSubArrayLen(self, s: int, nums: List[int]) -> int:
# 定义一个无限大的数
res = float("inf")
Sum = 0
index = 0
for i in range(len(nums)):
Sum += nums[i]
while Sum >= s:
res = min(res, i-index+1)
Sum -= nums[index]
index += 1
return 0 if res==float("inf") else res
```
## 相关题目推荐 ## 相关题目推荐
* 904.水果成篮 * 904.水果成篮
@ -170,24 +150,69 @@ class Solution {
Python Python
```python
class Solution:
def minSubArrayLen(self, s: int, nums: List[int]) -> int:
# 定义一个无限大的数
res = float("inf")
Sum = 0
index = 0
for i in range(len(nums)):
Sum += nums[i]
while Sum >= s:
res = min(res, i-index+1)
Sum -= nums[index]
index += 1
return 0 if res==float("inf") else res
```
Go Go
```go
func minSubArrayLen(target int, nums []int) int {
i := 0
l := len(nums) // 数组长度
sum := 0 // 子数组之和
result := l + 1 // 初始化返回长度为l+1目的是为了判断“不存在符合条件的子数组返回0”的情况
for j := 0; j < l; j++ {
sum += nums[j]
for sum >= target {
subLength := j - i + 1
if subLength < result {
result = subLength
}
sum -= nums[i]
i++
}
}
if result == l+1 {
return 0
} else {
return result
}
}
```
JavaScript: JavaScript:
```
var minSubArrayLen = (target, nums) => { ```js
let left = 0, right = 0,win = Infinity,sum = 0;
while(right < nums.length){ var minSubArrayLen = function(target, nums) {
sum += nums[right]; // 长度计算一次
const len = nums.length;
let l = r = sum = 0,
res = len + 1; // 子数组最大不会超过自身
while(r < len) {
sum += nums[r++];
// 窗口滑动
while(sum >= target) { while(sum >= target) {
win = right - left + 1 < win? right - left + 1 : win; // r始终为开区间 [l, r)
sum -= nums[left]; res = res < r - l ? res : r - l;
left++; sum-=nums[l++];
} }
right++;
} }
return win === Infinity? 0:win; return res > len ? 0 : res;
}; };
``` ```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 213.打家劫舍II ## 213.打家劫舍II
@ -98,11 +98,73 @@ public:
Java Java
```Java
class Solution {
public int rob(int[] nums) {
if (nums == null || nums.length == 0)
return 0;
int len = nums.length;
if (len == 1)
return nums[0];
return Math.max(robAction(nums, 0, len - 1), robAction(nums, 1, len));
}
int robAction(int[] nums, int start, int end) {
int x = 0, y = 0, z = 0;
for (int i = start; i < end; i++) {
y = z;
z = Math.max(y, x + nums[i]);
x = y;
}
return z;
}
}
```
Python Python
```Python
class Solution:
def rob(self, nums: List[int]) -> int:
if (n := len(nums)) == 0:
return 0
if n == 1:
return nums[0]
result1 = self.robRange(nums, 0, n - 2)
result2 = self.robRange(nums, 1, n - 1)
return max(result1 , result2)
def robRange(self, nums: List[int], start: int, end: int) -> int:
if end == start: return nums[start]
dp = [0] * len(nums)
dp[start] = nums[start]
dp[start + 1] = max(nums[start], nums[start + 1])
for i in range(start + 2, end + 1):
dp[i] = max(dp[i -2] + nums[i], dp[i - 1])
return dp[end]
```
javascipt:
```javascript
var rob = function(nums) {
const n = nums.length
if (n === 0) return 0
if (n === 1) return nums[0]
const result1 = robRange(nums, 0, n - 2)
const result2 = robRange(nums, 1, n - 1)
return Math.max(result1, result2)
};
const robRange = (nums, start, end) => {
if (end === start) return nums[start]
const dp = Array(nums.length).fill(0)
dp[start] = nums[start]
dp[start + 1] = Math.max(nums[start], nums[start + 1])
for (let i = start + 2; i <= end; i++) {
dp[i] = Math.max(dp[i - 2] + nums[i], dp[i - 1])
}
return dp[end]
}
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -94,7 +94,7 @@ void backtracking(int targetSum, int k, int sum, int startIndex)
所以 终止代码如下: 所以 终止代码如下:
``` ```C++
if (path.size() == k) { if (path.size() == k) {
if (sum == targetSum) result.push_back(path); if (sum == targetSum) result.push_back(path);
return; // 如果path.size() == k 但sum != targetSum 直接返回 return; // 如果path.size() == k 但sum != targetSum 直接返回
@ -112,7 +112,7 @@ if (path.size() == k) {
代码如下: 代码如下:
``` ```C++
for (int i = startIndex; i <= 9; i++) { for (int i = startIndex; i <= 9; i++) {
sum += i; sum += i;
path.push_back(i); path.push_back(i);
@ -126,7 +126,7 @@ for (int i = startIndex; i <= 9; i++) {
参照[关于回溯算法,你该了解这些!](https://mp.weixin.qq.com/s/gjSgJbNbd1eAA5WkA-HeWw)中的模板不难写出如下C++代码: 参照[关于回溯算法,你该了解这些!](https://mp.weixin.qq.com/s/gjSgJbNbd1eAA5WkA-HeWw)中的模板不难写出如下C++代码:
``` ```C++
class Solution { class Solution {
private: private:
vector<vector<int>> result; // 存放结果集 vector<vector<int>> result; // 存放结果集
@ -180,7 +180,7 @@ if (sum > targetSum) { // 剪枝操作
最后C++代码如下: 最后C++代码如下:
``` ```c++
class Solution { class Solution {
private: private:
vector<vector<int>> result; // 存放结果集 vector<vector<int>> result; // 存放结果集
@ -262,10 +262,66 @@ class Solution {
``` ```
Python Python
```py
class Solution:
def combinationSum3(self, k: int, n: int) -> List[List[int]]:
res = [] #存放结果集
path = [] #符合条件的结果
def findallPath(n,k,sum,startIndex):
if sum > n: return #剪枝操作
if sum == n and len(path) == k: #如果path.size() == k 但sum != n 直接返回
return res.append(path[:])
for i in range(startIndex,9-(k-len(path))+2): #剪枝操作
path.append(i)
sum += i
findallPath(n,k,sum,i+1) #注意i+1调整startIndex
sum -= i #回溯
path.pop() #回溯
findallPath(n,k,0,1)
return res
```
Go Go
javaScript:
```js
// 等差数列
var maxV = k => k * (9 + 10 - k) / 2;
var minV = k => k * (1 + k) / 2;
var combinationSum3 = function(k, n) {
if (k > 9 || k < 1) return [];
// if (n > maxV(k) || n < minV(k)) return [];
// if (n === maxV(k)) return [Array.from({length: k}).map((v, i) => 9 - i)];
// if (n === minV(k)) return [Array.from({length: k}).map((v, i) => i + 1)];
const res = [], path = [];
backtracking(k, n, 1, 0);
return res;
function backtracking(k, n, i, sum){
const len = path.length;
if (len > k || sum > n) return;
if (maxV(k - len) < n - sum) return;
if (minV(k - len) > n - sum) return;
if(len === k && sum == n) {
res.push(Array.from(path));
return;
}
const min = Math.min(n - sum, 9 + len - k + 1);
for(let a = i; a <= min; a++) {
path.push(a);
sum += a;
backtracking(k, n, a + 1, sum);
path.pop();
sum -= a;
}
}
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 222.完全二叉树的节点个数 ## 222.完全二叉树的节点个数
@ -240,9 +240,171 @@ class Solution {
Python Python
> 递归法:
```python
class Solution:
def countNodes(self, root: TreeNode) -> int:
return self.getNodesNum(root)
def getNodesNum(self, cur):
if not cur:
return 0
leftNum = self.getNodesNum(cur.left) #左
rightNum = self.getNodesNum(cur.right) #右
treeNum = leftNum + rightNum + 1 #中
return treeNum
```
> 递归法:精简版
```python
class Solution:
def countNodes(self, root: TreeNode) -> int:
if not root:
return 0
return 1 + self.countNodes(root.left) + self.countNodes(root.right)
```
> 迭代法:
```python
import collections
class Solution:
def countNodes(self, root: TreeNode) -> int:
queue = collections.deque()
if root:
queue.append(root)
result = 0
while queue:
size = len(queue)
for i in range(size):
node = queue.popleft()
result += 1 #记录节点数量
if node.left:
queue.append(node.left)
if node.right:
queue.append(node.right)
return result
```
> 完全二叉树
```python
class Solution:
def countNodes(self, root: TreeNode) -> int:
if not root:
return 0
left = root.left
right = root.right
leftHeight = 0 #这里初始为0是有目的的,为了下面求指数方便
rightHeight = 0
while left: #求左子树深度
left = left.left
leftHeight += 1
while right: #求右子树深度
right = right.right
rightHeight += 1
if leftHeight == rightHeight:
return (2 << leftHeight) - 1 #注意(2<<1) 相当于2^2所以leftHeight初始为0
return self.countNodes(root.left) + self.countNodes(root.right) + 1
```
Go Go
递归版本
```go
/**
* Definition for a binary tree node.
* type TreeNode struct {
* Val int
* Left *TreeNode
* Right *TreeNode
* }
*/
//本题直接就是求有多少个节点,无脑存进数组算长度就行了。
func countNodes(root *TreeNode) int {
if root == nil {
return 0
}
res := 1
if root.Right != nil {
res += countNodes(root.Right)
}
if root.Left != nil {
res += countNodes(root.Left)
}
return res
}
```
JavaScript:
递归版本
```javascript
var countNodes = function(root) {
//递归法计算二叉树节点数
// 1. 确定递归函数参数
const getNodeSum=function(node){
//2. 确定终止条件
if(node===null){
return 0;
}
//3. 确定单层递归逻辑
let leftNum=getNodeSum(node.left);
let rightNum=getNodeSum(node.right);
return leftNum+rightNum+1;
}
return getNodeSum(root);
};
```
迭代(层序遍历)版本
```javascript
var countNodes = function(root) {
//层序遍历
let queue=[];
if(root===null){
return 0;
}
queue.push(root);
let nodeNums=0;
while(queue.length){
let length=queue.length;
while(length--){
let node=queue.shift();
nodeNums++;
node.left&&queue.push(node.left);
node.right&&queue.push(node.right);
}
}
return nodeNums;
};
```
利用完全二叉树性质
```javascript
var countNodes = function(root) {
//利用完全二叉树的特点
if(root===null){
return 0;
}
let left=root.left;
let right=root.right;
let leftHeight=0,rightHeight=0;
while(left){
left=left.left;
leftHeight++;
}
while(right){
right=right.right;
rightHeight++;
}
if(leftHeight==rightHeight){
return Math.pow(2,leftHeight+1)-1;
}
return countNodes(root.left)+countNodes(root.right)+1;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -156,6 +156,7 @@ public:
Java Java
使用两个 Queue 实现
```java ```java
class MyStack { class MyStack {
@ -205,7 +206,94 @@ class MyStack {
* boolean param_4 = obj.empty(); * boolean param_4 = obj.empty();
*/ */
``` ```
使用两个 Deque 实现
```java
class MyStack {
// Deque 接口继承了 Queue 接口
// 所以 Queue 中的 add、poll、peek等效于 Deque 中的 addLast、pollFirst、peekFirst
Deque<Integer> que1; // 和栈中保持一样元素的队列
Deque<Integer> que2; // 辅助队列
/** Initialize your data structure here. */
public MyStack() {
que1 = new ArrayDeque<>();
que2 = new ArrayDeque<>();
}
/** Push element x onto stack. */
public void push(int x) {
que1.addLast(x);
}
/** Removes the element on top of the stack and returns that element. */
public int pop() {
int size = que1.size();
size--;
// 将 que1 导入 que2 ,但留下最后一个值
while (size-- > 0) {
que2.addLast(que1.peekFirst());
que1.pollFirst();
}
int res = que1.pollFirst();
// 将 que2 对象的引用赋给了 que1 ,此时 que1que2 指向同一个队列
que1 = que2;
// 如果直接操作 que2que1 也会受到影响,所以为 que2 分配一个新的空间
que2 = new ArrayDeque<>();
return res;
}
/** Get the top element. */
public int top() {
return que1.peekLast();
}
/** Returns whether the stack is empty. */
public boolean empty() {
return que1.isEmpty();
}
}
```
优化,使用一个 Deque 实现
```java
class MyStack {
// Deque 接口继承了 Queue 接口
// 所以 Queue 中的 add、poll、peek等效于 Deque 中的 addLast、pollFirst、peekFirst
Deque<Integer> que1;
/** Initialize your data structure here. */
public MyStack() {
que1 = new ArrayDeque<>();
}
/** Push element x onto stack. */
public void push(int x) {
que1.addLast(x);
}
/** Removes the element on top of the stack and returns that element. */
public int pop() {
int size = que1.size();
size--;
// 将 que1 导入 que2 ,但留下最后一个值
while (size-- > 0) {
que1.addLast(que1.peekFirst());
que1.pollFirst();
}
int res = que1.pollFirst();
return res;
}
/** Get the top element. */
public int top() {
return que1.peekLast();
}
/** Returns whether the stack is empty. */
public boolean empty() {
return que1.isEmpty();
}
}
```
Python Python
@ -269,8 +357,115 @@ class MyStack:
Go Go
javaScript:
使用数组push, shift模拟队列
```js
// 使用两个队列实现
/**
* Initialize your data structure here.
*/
var MyStack = function() {
this.queue1 = [];
this.queue2 = [];
};
/**
* Push element x onto stack.
* @param {number} x
* @return {void}
*/
MyStack.prototype.push = function(x) {
this.queue1.push(x);
};
/**
* Removes the element on top of the stack and returns that element.
* @return {number}
*/
MyStack.prototype.pop = function() {
// 减少两个队列交换的次数, 只有当queue1为空时交换两个队列
if(!this.queue1.length) {
[this.queue1, this.queue2] = [this.queue2, this.queue1];
}
while(this.queue1.length > 1) {
this.queue2.push(this.queue1.shift());
}
return this.queue1.shift();
};
/**
* Get the top element.
* @return {number}
*/
MyStack.prototype.top = function() {
const x = this.pop();
this.queue1.push(x);
return x;
};
/**
* Returns whether the stack is empty.
* @return {boolean}
*/
MyStack.prototype.empty = function() {
return !this.queue1.length && !this.queue2.length;
};
```
```js
// 使用一个队列实现
/**
* Initialize your data structure here.
*/
var MyStack = function() {
this.queue = [];
};
/**
* Push element x onto stack.
* @param {number} x
* @return {void}
*/
MyStack.prototype.push = function(x) {
this.queue.push(x);
};
/**
* Removes the element on top of the stack and returns that element.
* @return {number}
*/
MyStack.prototype.pop = function() {
let size = this.queue.length;
while(size-- > 1) {
this.queue.push(this.queue.shift());
}
return this.queue.shift();
};
/**
* Get the top element.
* @return {number}
*/
MyStack.prototype.top = function() {
const x = this.pop();
this.queue.push(x);
return x;
};
/**
* Returns whether the stack is empty.
* @return {boolean}
*/
MyStack.prototype.empty = function() {
return !this.queue.length;
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 226.翻转二叉树 ## 226.翻转二叉树
@ -230,6 +230,56 @@ class Solution {
Python Python
> 递归法:前序遍历
```python
class Solution:
def invertTree(self, root: TreeNode) -> TreeNode:
if not root:
return None
root.left, root.right = root.right, root.left #中
self.invertTree(root.left) #左
self.invertTree(root.right) #右
return root
```
> 迭代法:深度优先遍历(前序遍历)
```python
class Solution:
def invertTree(self, root: TreeNode) -> TreeNode:
if not root:
return root
st = []
st.append(root)
while st:
node = st.pop()
node.left, node.right = node.right, node.left #中
if node.right:
st.append(node.right) #右
if node.left:
st.append(node.left) #左
return root
```
> 迭代法:广度优先遍历(层序遍历)
```python
import collections
class Solution:
def invertTree(self, root: TreeNode) -> TreeNode:
queue = collections.deque() #使用deque()
if root:
queue.append(root)
while queue:
size = len(queue)
for i in range(size):
node = queue.popleft()
node.left, node.right = node.right, node.left #节点处理
if node.left:
queue.append(node.left)
if node.right:
queue.append(node.right)
return root
```
Go Go
```Go ```Go
func invertTree(root *TreeNode) *TreeNode { func invertTree(root *TreeNode) *TreeNode {
@ -247,7 +297,97 @@ func invertTree(root *TreeNode) *TreeNode {
} }
``` ```
JavaScript:
使用递归版本的前序遍历
```javascript
var invertTree = function(root) {
//1. 首先使用递归版本的前序遍历实现二叉树翻转
//交换节点函数
const inverNode=function(left,right){
let temp=left;
left=right;
right=temp;
//需要重新给root赋值一下
root.left=left;
root.right=right;
}
//确定递归函数的参数和返回值inverTree=function(root)
//确定终止条件
if(root===null){
return root;
}
//确定节点处理逻辑 交换
inverNode(root.left,root.right);
invertTree(root.left);
invertTree(root.right);
return root;
};
```
使用迭代版本(统一模板))的前序遍历:
```javascript
var invertTree = function(root) {
//我们先定义节点交换函数
const invertNode=function(root,left,right){
let temp=left;
left=right;
right=temp;
root.left=left;
root.right=right;
}
//使用迭代方法的前序遍历
let stack=[];
if(root===null){
return root;
}
stack.push(root);
while(stack.length){
let node=stack.pop();
if(node!==null){
//前序遍历顺序中左右 入栈顺序是前序遍历的倒序右左中
node.right&&stack.push(node.right);
node.left&&stack.push(node.left);
stack.push(node);
stack.push(null);
}else{
node=stack.pop();
//节点处理逻辑
invertNode(node,node.left,node.right);
}
}
return root;
};
```
使用层序遍历:
```javascript
var invertTree = function(root) {
//我们先定义节点交换函数
const invertNode=function(root,left,right){
let temp=left;
left=right;
right=temp;
root.left=left;
root.right=right;
}
//使用层序遍历
let queue=[];
if(root===null){
return root;
}
queue.push(root);
while(queue.length){
let length=queue.length;
while(length--){
let node=queue.shift();
//节点处理逻辑
invertNode(node,node.left,node.right);
node.left&&queue.push(node.left);
node.right&&queue.push(node.right);
}
}
return root;
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 工作上一定没人这么搞,但是考察对栈、队列理解程度的好题 > 工作上一定没人这么搞,但是考察对栈、队列理解程度的好题
@ -131,6 +131,101 @@ public:
Java Java
使用Stack(堆栈)同名方法:
```java
class MyQueue {
// java中的 Stack 有设计上的缺陷,官方推荐使用 Deque(双端队列) 代替 Stack
Deque<Integer> stIn;
Deque<Integer> stOut;
/** Initialize your data structure here. */
public MyQueue() {
stIn = new ArrayDeque<>();
stOut = new ArrayDeque<>();
}
/** Push element x to the back of queue. */
public void push(int x) {
stIn.push(x);
}
/** Removes the element from in front of queue and returns that element. */
public int pop() {
// 只要 stOut 为空,那么就应该将 stIn 中所有的元素倒腾到 stOut 中
if (stOut.isEmpty()) {
while (!stIn.isEmpty()) {
stOut.push(stIn.pop());
}
}
// 再返回 stOut 中的元素
return stOut.pop();
}
/** Get the front element. */
public int peek() {
// 直接使用已有的pop函数
int res = this.pop();
// 因为pop函数弹出了元素res所以再添加回去
stOut.push(res);
return res;
}
/** Returns whether the queue is empty. */
public boolean empty() {
// 当 stIn 栈为空时,说明没有元素可以倒腾到 stOut 栈了
// 并且 stOut 栈也为空时,说明没有以前从 stIn 中倒腾到的元素了
return stIn.isEmpty() && stOut.isEmpty();
}
}
```
个人习惯写法使用Deque通用api
```java
class MyQueue {
// java中的 Stack 有设计上的缺陷,官方推荐使用 Deque(双端队列) 代替 Stack
// Deque 中的 addFirst、removeFirst、peekFirst 等方法等效于 Stack(堆栈) 中的 push、pop、peek
Deque<Integer> stIn;
Deque<Integer> stOut;
/** Initialize your data structure here. */
public MyQueue() {
stIn = new ArrayDeque<>();
stOut = new ArrayDeque<>();
}
/** Push element x to the back of queue. */
public void push(int x) {
stIn.addLast(x);
}
/** Removes the element from in front of queue and returns that element. */
public int pop() {
// 只要 stOut 为空,那么就应该将 stIn 中所有的元素倒腾到 stOut 中
if (stOut.isEmpty()) {
while (!stIn.isEmpty()) {
stOut.addLast(stIn.pollLast());
}
}
// 再返回 stOut 中的元素
return stOut.pollLast();
}
/** Get the front element. */
public int peek() {
// 直接使用已有的pop函数
int res = this.pop();
// 因为pop函数弹出了元素res所以再添加回去
stOut.addLast(res);
return res;
}
/** Returns whether the queue is empty. */
public boolean empty() {
// 当 stIn 栈为空时,说明没有元素可以倒腾到 stOut 栈了
// 并且 stOut 栈也为空时,说明没有以前从 stIn 中倒腾到的元素了
return stIn.isEmpty() && stOut.isEmpty();
}
}
```
```java ```java
class MyQueue { class MyQueue {
@ -187,9 +282,175 @@ class MyQueue {
Python Python
```python
# 使用两个栈实现先进先出的队列
class MyQueue:
def __init__(self):
"""
Initialize your data structure here.
"""
self.stack1 = list()
self.stack2 = list()
def push(self, x: int) -> None:
"""
Push element x to the back of queue.
"""
# self.stack1用于接受元素
self.stack1.append(x)
def pop(self) -> int:
"""
Removes the element from in front of queue and returns that element.
"""
# self.stack2用于弹出元素如果self.stack2为[],则将self.stack1中元素全部弹出给self.stack2
if self.stack2 == []:
while self.stack1:
tmp = self.stack1.pop()
self.stack2.append(tmp)
return self.stack2.pop()
def peek(self) -> int:
"""
Get the front element.
"""
if self.stack2 == []:
while self.stack1:
tmp = self.stack1.pop()
self.stack2.append(tmp)
return self.stack2[-1]
def empty(self) -> bool:
"""
Returns whether the queue is empty.
"""
return self.stack1 == [] and self.stack2 == []
```
Go Go
```Go
type MyQueue struct {
stack []int
back []int
}
/** Initialize your data structure here. */
func Constructor() MyQueue {
return MyQueue{
stack: make([]int, 0),
back: make([]int, 0),
}
}
/** Push element x to the back of queue. */
func (this *MyQueue) Push(x int) {
for len(this.back) != 0 {
val := this.back[len(this.back)-1]
this.back = this.back[:len(this.back)-1]
this.stack = append(this.stack, val)
}
this.stack = append(this.stack, x)
}
/** Removes the element from in front of queue and returns that element. */
func (this *MyQueue) Pop() int {
for len(this.stack) != 0 {
val := this.stack[len(this.stack)-1]
this.stack = this.stack[:len(this.stack)-1]
this.back = append(this.back, val)
}
if len(this.back) == 0 {
return 0
}
val := this.back[len(this.back)-1]
this.back = this.back[:len(this.back)-1]
return val
}
/** Get the front element. */
func (this *MyQueue) Peek() int {
for len(this.stack) != 0 {
val := this.stack[len(this.stack)-1]
this.stack = this.stack[:len(this.stack)-1]
this.back = append(this.back, val)
}
if len(this.back) == 0 {
return 0
}
val := this.back[len(this.back)-1]
return val
}
/** Returns whether the queue is empty. */
func (this *MyQueue) Empty() bool {
return len(this.stack) == 0 && len(this.back) == 0
}
/**
* Your MyQueue object will be instantiated and called as such:
* obj := Constructor();
* obj.Push(x);
* param_2 := obj.Pop();
* param_3 := obj.Peek();
* param_4 := obj.Empty();
*/
```
javaScript:
```js
// 使用两个数组的栈方法push, pop 实现队列
/**
* Initialize your data structure here.
*/
var MyQueue = function() {
this.stack1 = [];
this.stack2 = [];
};
/**
* Push element x to the back of queue.
* @param {number} x
* @return {void}
*/
MyQueue.prototype.push = function(x) {
this.stack1.push(x);
};
/**
* Removes the element from in front of queue and returns that element.
* @return {number}
*/
MyQueue.prototype.pop = function() {
const size = this.stack2.length;
if(size) {
return this.stack2.pop();
}
while(this.stack1.length) {
this.stack2.push(this.stack1.pop());
}
return this.stack2.pop();
};
/**
* Get the front element.
* @return {number}
*/
MyQueue.prototype.peek = function() {
const x = this.pop();
this.stack2.push(x);
return x;
};
/**
* Returns whether the queue is empty.
* @return {boolean}
*/
MyQueue.prototype.empty = function() {
return !this.stack1.length && !this.stack2.length
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 235. 二叉搜索树的最近公共祖先 ## 235. 二叉搜索树的最近公共祖先
@ -247,8 +247,23 @@ class Solution {
``` ```
Python Python
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, x):
# self.val = x
# self.left = None
# self.right = None
class Solution:
def lowestCommonAncestor(self, root: 'TreeNode', p: 'TreeNode', q: 'TreeNode') -> 'TreeNode':
if not root: return root //中
if root.val >p.val and root.val > q.val:
return self.lowestCommonAncestor(root.left,p,q) //左
elif root.val < p.val and root.val < q.val:
return self.lowestCommonAncestor(root.right,p,q) //右
else: return root
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 本来是打算将二叉树和二叉搜索树的公共祖先问题一起讲,后来发现篇幅过长了,只能先说一说二叉树的公共祖先问题。 > 本来是打算将二叉树和二叉搜索树的公共祖先问题一起讲,后来发现篇幅过长了,只能先说一说二叉树的公共祖先问题。
@ -263,10 +263,53 @@ class Solution {
``` ```
Python Python
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, x):
# self.val = x
# self.left = None
# self.right = None
//递归
class Solution:
def lowestCommonAncestor(self, root: 'TreeNode', p: 'TreeNode', q: 'TreeNode') -> 'TreeNode':
if not root or root == p or root == q: return root //找到了节点p或者q或者遇到空节点
left = self.lowestCommonAncestor(root.left,p,q) //左
right = self.lowestCommonAncestor(root.right,p,q) //右
if left and right: return root //中: left和right不为空root就是最近公共节点
elif left and not right: return left //目标节点是通过left返回的
elif not left and right: return right //目标节点是通过right返回的
else: return None //没找到
```
Go Go
```Go
func lowestCommonAncestor(root, p, q *TreeNode) *TreeNode {
// check
if root == nil {
return root
}
// 相等 直接返回root节点即可
if root == p || root == q {
return root
}
// Divide
left := lowestCommonAncestor(root.Left, p, q)
right := lowestCommonAncestor(root.Right, p, q)
// Conquer
// 左右两边都不为空,则根节点为祖先
if left != nil && right != nil {
return root
}
if left != nil {
return left
}
if right != nil {
return right
}
return nil
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -263,11 +263,159 @@ class Solution {
``` ```
Python Python
```python
class MyQueue: #单调队列(从大到小
def __init__(self):
self.queue = [] #使用list来实现单调队列
#每次弹出的时候,比较当前要弹出的数值是否等于队列出口元素的数值,如果相等则弹出。
#同时pop之前判断队列当前是否为空
def pop(self, value):
if self.queue and value == self.queue[0]:
self.queue.pop(0)#list.pop()时间复杂度为O(n),这里可以使用collections.deque()
#如果push的数值大于入口元素的数值那么就将队列后端的数值弹出直到push的数值小于等于队列入口元素的数值为止。
#这样就保持了队列里的数值是单调从大到小的了
def push(self, value):
while self.queue and value > self.queue[-1]:
self.queue.pop()
self.queue.append(value)
#查询当前队列里的最大值 直接返回队列前端也就是front就可以了。
def front(self):
return self.queue[0]
class Solution:
def maxSlidingWindow(self, nums: List[int], k: int) -> List[int]:
que = MyQueue()
result = []
for i in range(k): #先将前k的元素放进队列
que.push(nums[i])
result.append(que.front()) #result 记录前k的元素的最大值
for i in range(k, len(nums)):
que.pop(nums[i - k]) #滑动窗口移除最前面元素
que.push(nums[i]) #滑动窗口前加入最后面的元素
result.append(que.front()) #记录对应的最大值
return result
```
Go Go
```go
func maxSlidingWindow(nums []int, k int) []int {
var queue []int
var rtn []int
for f := 0; f < len(nums); f++ {
//维持队列递减, 将 k 插入合适的位置, queue中 <=k 的 元素都不可能是窗口中的最大值, 直接弹出
for len(queue) > 0 && nums[f] > nums[queue[len(queue)-1]] {
queue = queue[:len(queue)-1]
}
// 等大的后来者也应入队
if len(queue) == 0 || nums[f] <= nums[queue[len(queue)-1]] {
queue = append(queue, f)
}
if f >= k - 1 {
rtn = append(rtn, nums[queue[0]])
//弹出离开窗口的队首
if f - k + 1 == queue[0] {
queue = queue[1:]
}
}
}
return rtn
}
```
```go
// 封装单调队列的方式解题
type MyQueue struct {
queue []int
}
func NewMyQueue() *MyQueue {
return &MyQueue{
queue: make([]int, 0),
}
}
func (m *MyQueue) Front() int {
return m.queue[0]
}
func (m *MyQueue) Back() int {
return m.queue[len(m.queue)-1]
}
func (m *MyQueue) Empty() bool {
return len(m.queue) == 0
}
func (m *MyQueue) Push(val int) {
for !m.Empty() && val > m.Back() {
m.queue = m.queue[:len(m.queue)-1]
}
m.queue = append(m.queue, val)
}
func (m *MyQueue) Pop(val int) {
if !m.Empty() && val == m.Front() {
m.queue = m.queue[1:]
}
}
func maxSlidingWindow(nums []int, k int) []int {
queue := NewMyQueue()
length := len(nums)
res := make([]int, 0)
// 先将前k个元素放入队列
for i := 0; i < k; i++ {
queue.Push(nums[i])
}
// 记录前k个元素的最大值
res = append(res, queue.Front())
for i := k; i < length; i++ {
// 滑动窗口移除最前面的元素
queue.Pop(nums[i-k])
// 滑动窗口添加最后面的元素
queue.Push(nums[i])
// 记录最大值
res = append(res, queue.Front())
}
return res
}
```
Javascript:
```javascript
var maxSlidingWindow = function (nums, k) {
// 队列数组(存放的是元素下标,为了取值方便)
const q = [];
// 结果数组
const ans = [];
for (let i = 0; i < nums.length; i++) {
// 若队列不为空,且当前元素大于等于队尾所存下标的元素,则弹出队尾
while (q.length && nums[i] >= nums[q[q.length - 1]]) {
q.pop();
}
// 入队当前元素下标
q.push(i);
// 判断当前最大值(即队首元素)是否在窗口中,若不在便将其出队
while (q[0] <= i - k) {
q.shift();
}
// 当达到窗口大小时便开始向结果中添加数据
if (i >= k - 1) ans.push(nums[q[0]]);
}
return ans;
};
```
----------------------- -----------------------

View File

@ -1,26 +1,33 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 数组就是简单的哈希表,但是数组的大小可不是无限开辟的 > 数组就是简单的哈希表,但是数组的大小可不是无限开辟的
# 242.有效的字母异位词 ## 242.有效的字母异位词
https://leetcode-cn.com/problems/valid-anagram/ https://leetcode-cn.com/problems/valid-anagram/
给定两个字符串 s 和 t ,编写一个函数来判断 t 是否是 s 的字母异位词。 给定两个字符串 s 和 t ,编写一个函数来判断 t 是否是 s 的字母异位词。
![](https://img-blog.csdnimg.cn/202008171902298.png) 示例 1:
输入: s = "anagram", t = "nagaram"
输出: true
示例 2:
输入: s = "rat", t = "car"
输出: false
**说明:** **说明:**
你可以假设字符串只包含小写字母。 你可以假设字符串只包含小写字母。
# 思路 ## 思路
先看暴力的解法两层for循环同时还要记录字符是否重复出现很明显时间复杂度是 O(n^2)。 先看暴力的解法两层for循环同时还要记录字符是否重复出现很明显时间复杂度是 O(n^2)。
@ -52,7 +59,6 @@ https://leetcode-cn.com/problems/valid-anagram/
时间复杂度为O(n)空间上因为定义是的一个常量大小的辅助数组所以空间复杂度为O(1)。 时间复杂度为O(n)空间上因为定义是的一个常量大小的辅助数组所以空间复杂度为O(1)。
看完这篇哈希表总结:[哈希表:总结篇!(每逢总结必经典)](https://mp.weixin.qq.com/s/1s91yXtarL-PkX07BfnwLg),详细就可以哈希表的各种用法非常清晰了。
C++ 代码如下: C++ 代码如下:
```C++ ```C++
@ -107,7 +113,22 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def isAnagram(self, s: str, t: str) -> bool:
record = [0] * 26
for i in range(len(s)):
#并不需要记住字符a的ASCII,只要求出一个相对数值就可以了
record[ord(s[i]) - ord("a")] += 1
print(record)
for i in range(len(t)):
record[ord(t[i]) - ord("a")] -= 1
for i in range(26):
if record[i] != 0:
#record数组如果有的元素不为零0说明字符串s和t 一定是谁多了字符或者谁少了字符。
return False
return True
```
Go Go
```go ```go
@ -134,6 +155,35 @@ func isAnagram(s string, t string) bool {
} }
``` ```
javaScript:
```js
/**
* @param {string} s
* @param {string} t
* @return {boolean}
*/
var isAnagram = function(s, t) {
if(s.length !== t.length) return false;
const resSet = new Array(26).fill(0);
const base = "a".charCodeAt();
for(const i of s) {
resSet[i.charCodeAt() - base]++;
}
for(const i of t) {
if(!resSet[i.charCodeAt() - base]) return false;
resSet[i.charCodeAt() - base]--;
}
return true;
};
```
## 相关题目
* 383.赎金信
* 49.字母异位词分组
* 438.找到字符串中所有字母异位词
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 以为只用了递归,其实还用了回溯 > 以为只用了递归,其实还用了回溯
@ -77,7 +77,7 @@ if (cur->left == NULL && cur->right == NULL) {
这里我们先使用vector<int>结构的path容器来记录路径那么终止处理逻辑如下 这里我们先使用vector<int>结构的path容器来记录路径那么终止处理逻辑如下
``` ```C++
if (cur->left == NULL && cur->right == NULL) { // 遇到叶子节点 if (cur->left == NULL && cur->right == NULL) { // 遇到叶子节点
string sPath; string sPath;
for (int i = 0; i < path.size() - 1; i++) { // 将path里记录的路径转为string格式 for (int i = 0; i < path.size() - 1; i++) { // 将path里记录的路径转为string格式
@ -113,7 +113,7 @@ if (cur->right) {
那么回溯要怎么回溯呢,一些同学会这么写,如下: 那么回溯要怎么回溯呢,一些同学会这么写,如下:
``` ```C++
if (cur->left) { if (cur->left) {
traversal(cur->left, path, result); traversal(cur->left, path, result);
} }
@ -129,7 +129,7 @@ path.pop_back();
那么代码应该这么写: 那么代码应该这么写:
``` ```C++
if (cur->left) { if (cur->left) {
traversal(cur->left, path, result); traversal(cur->left, path, result);
path.pop_back(); // 回溯 path.pop_back(); // 回溯
@ -324,10 +324,57 @@ class Solution {
``` ```
Python Python
```Python
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
class Solution:
def binaryTreePaths(self, root: TreeNode) -> List[str]:
path=[]
res=[]
def backtrace(root, path):
if not root:return
path.append(root.val)
if (not root.left)and (not root.right):
res.append(path[:])
ways=[]
if root.left:ways.append(root.left)
if root.right:ways.append(root.right)
for way in ways:
backtrace(way,path)
path.pop()
backtrace(root,path)
return ["->".join(list(map(str,i))) for i in res]
```
Go Go
JavaScript:
1.递归版本
```javascript
var binaryTreePaths = function(root) {
//递归遍历+递归三部曲
let res=[];
//1. 确定递归函数 函数参数
const getPath=function(node,curPath){
//2. 确定终止条件,到叶子节点就终止
if(node.left===null&&node.right===null){
curPath+=node.val;
res.push(curPath);
return ;
}
//3. 确定单层递归逻辑
curPath+=node.val+'->';
node.left&&getPath(node.left,curPath);
node.right&&getPath(node.right,curPath);
}
getPath(root,'');
return res;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 动态规划:一样的套路,再求一次完全平方数 # 动态规划:一样的套路,再求一次完全平方数
## 279.完全平方数 ## 279.完全平方数
@ -26,7 +26,7 @@
输入n = 13 输入n = 13
输出2 输出2
解释13 = 4 + 9 解释13 = 4 + 9
 
提示: 提示:
* 1 <= n <= 10^4 * 1 <= n <= 10^4
@ -184,9 +184,89 @@ class Solution {
Python Python
```python3
class Solution:
def numSquares(self, n: int) -> int:
'''版本一'''
# 初始化
nums = [i**2 for i in range(1, n + 1) if i**2 <= n]
dp = [10**4]*(n + 1)
dp[0] = 0
# 遍历背包
for j in range(1, n + 1):
# 遍历物品
for num in nums:
if j >= num:
dp[j] = min(dp[j], dp[j - num] + 1)
return dp[n]
def numSquares1(self, n: int) -> int:
'''版本二'''
# 初始化
nums = [i**2 for i in range(1, n + 1) if i**2 <= n]
dp = [10**4]*(n + 1)
dp[0] = 0
# 遍历物品
for num in nums:
# 遍历背包
for j in range(num, n + 1)
dp[j] = min(dp[j], dp[j - num] + 1)
return dp[n]
```
Go Go
```go
// 版本一,先遍历物品, 再遍历背包
func numSquares1(n int) int {
//定义
dp := make([]int, n+1)
// 初始化
dp[0] = 0
for i := 1; i <= n; i++ {
dp[i] = math.MaxInt32
}
// 遍历物品
for i := 1; i <= n; i++ {
// 遍历背包
for j := i*i; j <= n; j++ {
dp[j] = min(dp[j], dp[j-i*i]+1)
}
}
return dp[n]
}
// 版本二,先遍历背包, 再遍历物品
func numSquares2(n int) int {
//定义
dp := make([]int, n+1)
// 初始化
dp[0] = 0
// 遍历背包
for j := 1; j <= n; j++ {
//初始化
dp[j] = math.MaxInt32
// 遍历物品
for i := 1; i <= n; i++ {
if j >= i*i {
dp[j] = min(dp[j], dp[j-i*i]+1)
}
}
}
return dp[n]
}
func min(a, b int) int {
if a < b {
return a
}
return b
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 300.最长递增子序列 ## 300.最长递增子序列
@ -98,8 +98,6 @@ public:
}; };
``` ```
杨老师的这个专栏很不错他本身也是Oracle 首席工程师对Java有极其深刻的理解讲的内容很硬核适合使用Java语言的录友们用来进阶作为面试突击手册非常合适 所以推荐给大家现在下单输入口令javahexin可以省40元那[机智]
## 总结 ## 总结
本题最关键的是要想到dp[i]由哪些状态可以推出来并取最大值那么很自然就能想到递推公式dp[i] = max(dp[i], dp[j] + 1); 本题最关键的是要想到dp[i]由哪些状态可以推出来并取最大值那么很自然就能想到递推公式dp[i] = max(dp[i], dp[j] + 1);
@ -110,14 +108,71 @@ public:
Java Java
```Java
class Solution {
public int lengthOfLIS(int[] nums) {
int[] dp = new int[nums.length];
Arrays.fill(dp, 1);
for (int i = 0; i < dp.length; i++) {
for (int j = 0; j < i; j++) {
if (nums[i] > nums[j]) {
dp[i] = Math.max(dp[i], dp[j] + 1);
}
}
}
int res = 0;
for (int i = 0; i < dp.length; i++) {
res = Math.max(res, dp[i]);
}
return res;
}
}
```
Python Python
```python
class Solution:
def lengthOfLIS(self, nums: List[int]) -> int:
if len(nums) <= 1:
return len(nums)
dp = [1] * len(nums)
result = 0
for i in range(1, len(nums)):
for j in range(0, i):
if nums[i] > nums[j]:
dp[i] = max(dp[i], dp[j] + 1)
result = max(result, dp[i]) #取长的子序列
return result
```
Go Go
```go
func lengthOfLIS(nums []int ) int {
dp := []int{}
for _, num := range nums {
if len(dp) ==0 || dp[len(dp) - 1] < num {
dp = append(dp, num)
} else {
l, r := 0, len(dp) - 1
pos := r
for l <= r {
mid := (l + r) >> 1
if dp[mid] >= num {
pos = mid;
r = mid - 1
} else {
l = mid + 1
}
}
dp[pos] = num
}//二分查找
}
return len(dp)
}
```
*复杂度分析*
- 时间复杂度O(nlogn)。数组 nums 的长度为 n我们依次用数组中的元素去更新 dp 数组,相当于插入最后递增的元素,而更新 dp 数组时需要进行 O(logn) 的二分搜索,所以总时间复杂度为 O(nlogn)。
- 空间复杂度O(n),需要额外使用长度为 n 的 dp 数组。
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 309.最佳买卖股票时机含冷冻期 ## 309.最佳买卖股票时机含冷冻期
@ -159,12 +159,51 @@ public:
## 其他语言版本 ## 其他语言版本
Java Java
```java
class Solution {
public int maxProfit(int[] prices) {
if (prices == null || prices.length < 2) {
return 0;
}
int[][] dp = new int[prices.length][2];
// bad case
dp[0][0] = 0;
dp[0][1] = -prices[0];
dp[1][0] = Math.max(dp[0][0], dp[0][1] + prices[1]);
dp[1][1] = Math.max(dp[0][1], -prices[1]);
for (int i = 2; i < prices.length; i++) {
// dp公式
dp[i][0] = Math.max(dp[i - 1][0], dp[i - 1][1] + prices[i]);
dp[i][1] = Math.max(dp[i - 1][1], dp[i - 2][0] - prices[i]);
}
return dp[prices.length - 1][0];
}
}
```
Python Python
```python
class Solution:
def maxProfit(self, prices: List[int]) -> int:
n = len(prices)
if n == 0:
return 0
dp = [[0] * 4 for _ in range(n)]
dp[0][0] = -prices[0] #持股票
for i in range(1, n):
dp[i][0] = max(dp[i-1][0], max(dp[i-1][3], dp[i-1][1]) - prices[i])
dp[i][1] = max(dp[i-1][1], dp[i-1][3])
dp[i][2] = dp[i-1][0] + prices[i]
dp[i][3] = dp[i-1][2]
return max(dp[n-1][3], dp[n-1][1], dp[n-1][2])
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 动态规划: 给我个机会,我再兑换一次零钱 # 动态规划: 给我个机会,我再兑换一次零钱
## 322. 零钱兑换 ## 322. 零钱兑换
@ -35,7 +35,7 @@
示例 5 示例 5
输入coins = [1], amount = 2 输入coins = [1], amount = 2
输出2 输出2
 
提示: 提示:
* 1 <= coins.length <= 12 * 1 <= coins.length <= 12
@ -209,9 +209,100 @@ class Solution {
Python Python
```python3
class Solution:
def coinChange(self, coins: List[int], amount: int) -> int:
'''版本一'''
# 初始化
dp = [amount + 1]*(amount + 1)
dp[0] = 0
# 遍历物品
for coin in coins:
# 遍历背包
for j in range(coin, amount + 1):
dp[j] = min(dp[j], dp[j - coin] + 1)
return dp[amount] if dp[amount] < amount + 1 else -1
def coinChange1(self, coins: List[int], amount: int) -> int:
'''版本二'''
# 初始化
dp = [amount + 1]*(amount + 1)
dp[0] = 0
# 遍历物品
for j in range(1, amount + 1):
# 遍历背包
for coin in coins:
if j >= coin:
dp[j] = min(dp[j], dp[j - coin] + 1)
return dp[amount] if dp[amount] < amount + 1 else -1
```
Go Go
```go
// 版本一, 先遍历物品,再遍历背包
func coinChange1(coins []int, amount int) int {
dp := make([]int, amount+1)
// 初始化dp[0]
dp[0] = 0
// 初始化为math.MaxInt32
for j := 1; j <= amount; j++ {
dp[j] = math.MaxInt32
}
// 遍历物品
for i := 0; i < len(coins); i++ {
// 遍历背包
for j := coins[i]; j <= amount; j++ {
if dp[j-coins[i]] != math.MaxInt32 {
// 推导公式
dp[j] = min(dp[j], dp[j-coins[i]]+1)
//fmt.Println(dp,j,i)
}
}
}
// 没找到能装满背包的, 就返回-1
if dp[amount] == math.MaxInt32 {
return -1
}
return dp[amount]
}
// 版本二,先遍历背包,再遍历物品
func coinChange2(coins []int, amount int) int {
dp := make([]int, amount+1)
// 初始化dp[0]
dp[0] = 0
// 遍历背包,从1开始
for j := 1; j <= amount; j++ {
// 初始化为math.MaxInt32
dp[j] = math.MaxInt32
// 遍历物品
for i := 0; i < len(coins); i++ {
if j >= coins[i] && dp[j-coins[i]] != math.MaxInt32 {
// 推导公式
dp[j] = min(dp[j], dp[j-coins[i]]+1)
//fmt.Println(dp)
}
}
}
// 没找到能装满背包的, 就返回-1
if dp[amount] == math.MaxInt32 {
return -1
}
return dp[amount]
}
func min(a, b int) int {
if a < b {
return a
}
return b
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 这也可以用回溯法? 其实深搜和回溯也是相辅相成的,毕竟都用递归。 > 这也可以用回溯法? 其实深搜和回溯也是相辅相成的,毕竟都用递归。
@ -399,6 +399,49 @@ char ** findItinerary(char *** tickets, int ticketsSize, int* ticketsColSize, in
} }
``` ```
Javascript:
```Javascript
var findItinerary = function(tickets) {
let result = ['JFK']
let map = {}
for (const tickt of tickets) {
const [from, to] = tickt
if (!map[from]) {
map[from] = []
}
map[from].push(to)
}
for (const city in map) {
// 对到达城市列表排序
map[city].sort()
}
function backtracing() {
if (result.length === tickets.length + 1) {
return true
}
if (!map[result[result.length - 1]] || !map[result[result.length - 1]].length) {
return false
}
for(let i = 0 ; i < map[result[result.length - 1]].length; i++) {
let city = map[result[result.length - 1]][i]
// 删除已走过航线,防止死循环
map[result[result.length - 1]].splice(i, 1)
result.push(city)
if (backtracing()) {
return true
}
result.pop()
map[result[result.length - 1]].splice(i, 0, city)
}
}
backtracing()
return result
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 337.打家劫舍 III ## 337.打家劫舍 III
@ -218,10 +218,94 @@ public:
Java Java
```Java
class Solution {
// 1.递归去偷,超时
public int rob(TreeNode root) {
if (root == null)
return 0;
int money = root.val;
if (root.left != null) {
money += rob(root.left.left) + rob(root.left.right);
}
if (root.right != null) {
money += rob(root.right.left) + rob(root.right.right);
}
return Math.max(money, rob(root.left) + rob(root.right));
}
// 2.递归去偷,记录状态
// 执行用时3 ms , 在所有 Java 提交中击败了 56.24% 的用户
public int rob1(TreeNode root) {
Map<TreeNode, Integer> memo = new HashMap<>();
return robAction(root, memo);
}
int robAction(TreeNode root, Map<TreeNode, Integer> memo) {
if (root == null)
return 0;
if (memo.containsKey(root))
return memo.get(root);
int money = root.val;
if (root.left != null) {
money += robAction(root.left.left, memo) + robAction(root.left.right, memo);
}
if (root.right != null) {
money += robAction(root.right.left, memo) + robAction(root.right.right, memo);
}
int res = Math.max(money, robAction(root.left, memo) + robAction(root.right, memo));
memo.put(root, res);
return res;
}
// 3.状态标记递归
// 执行用时0 ms , 在所有 Java 提交中击败了 100% 的用户
// 不偷Max(左孩子不偷,左孩子偷) + Max(又孩子不偷,右孩子偷)
// root[0] = Math.max(rob(root.left)[0], rob(root.left)[1]) +
// Math.max(rob(root.right)[0], rob(root.right)[1])
// 偷:左孩子不偷+ 右孩子不偷 + 当前节点偷
// root[1] = rob(root.left)[0] + rob(root.right)[0] + root.val;
public int rob3(TreeNode root) {
int[] res = robAction1(root);
return Math.max(res[0], res[1]);
}
int[] robAction1(TreeNode root) {
int res[] = new int[2];
if (root == null)
return res;
int[] left = robAction1(root.left);
int[] right = robAction1(root.right);
res[0] = Math.max(left[0], left[1]) + Math.max(right[0], right[1]);
res[1] = root.val + left[0] + right[0];
return res;
}
}
```
Python Python
> 动态规划
```python
class Solution:
def rob(self, root: TreeNode) -> int:
result = self.robTree(root)
return max(result[0], result[1])
#长度为2的数组0不偷1
def robTree(self, cur):
if not cur:
return (0, 0) #这里返回tuple, 也可以返回list
left = self.robTree(cur.left)
right = self.robTree(cur.right)
#偷cur
val1 = cur.val + left[0] + right[0]
#不偷cur
val2 = max(left[0], left[1]) + max(right[0], right[1])
return (val2, val1)
```
Go Go

View File

@ -1,13 +1,15 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 343. 整数拆分 ## 343. 整数拆分
题目链接https://leetcode-cn.com/problems/integer-break/
给定一个正整数 n将其拆分为至少两个正整数的和并使这些整数的乘积最大化。 返回你可以获得的最大乘积。 给定一个正整数 n将其拆分为至少两个正整数的和并使这些整数的乘积最大化。 返回你可以获得的最大乘积。
示例 1: 示例 1:
@ -49,11 +51,14 @@ dp[i]的定义讲贯彻整个解题过程,下面哪一步想不懂了,就想
**那有同学问了j怎么就不拆分呢** **那有同学问了j怎么就不拆分呢**
j是从1开始遍历拆分j的情况在遍历j的过程中其实都计算过了。 j是从1开始遍历拆分j的情况在遍历j的过程中其实都计算过了。那么从1遍历j比较(i - j) * j和dp[i - j] * j 取最大的。递推公式dp[i] = max(dp[i], max((i - j) * j, dp[i - j] * j));
那么从1遍历j比较(i - j) * j和dp[i - j] * j 取最大的。 也可以这么理解j * (i - j) 是单纯的把整数拆分为两个数相乘而j * dp[i - j]是拆分成两个以及两个以上的个数相乘。
如果定义dp[i - j] * dp[j] 也是默认将一个数强制拆成4份以及4份以上了。
所以递推公式dp[i] = max({dp[i], (i - j) * j, dp[i - j] * j});
递推公式dp[i] = max(dp[i], max((i - j) * j, dp[i - j] * j));
3. dp的初始化 3. dp的初始化
@ -185,11 +190,38 @@ public:
Java Java
```Java
class Solution {
public int integerBreak(int n) {
//dp[i]为正整数i拆分结果的最大乘积
int[] dp = new int[n+1];
dp[2] = 1;
for (int i = 3; i <= n; ++i) {
for (int j = 1; j < i - 1; ++j) {
//j*(i-j)代表把i拆分为j和i-j两个数相乘
//j*dp[i-j]代表把i拆分成j和继续把(i-j)这个数拆分,取(i-j)拆分结果中的最大乘积与j相乘
dp[i] = Math.max(dp[i], Math.max(j * (i - j), j * dp[i - j]));
}
}
return dp[n];
}
}
```
Python Python
```python
class Solution:
def integerBreak(self, n: int) -> int:
dp = [0] * (n + 1)
dp[2] = 1
for i in range(3, n + 1):
# 假设对正整数 i 拆分出的第一个正整数是 j1 <= j < i则有以下两种方案
# 1) 将 i 拆分成 j 和 ij 的和,且 ij 不再拆分成多个正整数,此时的乘积是 j * (i-j)
# 2) 将 i 拆分成 j 和 ij 的和,且 ij 继续拆分成多个正整数,此时的乘积是 j * dp[i-j]
for j in range(1, i - 1):
dp[i] = max(dp[i], max(j * (i - j), j * dp[i - j]))
return dp[n]
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -157,7 +157,18 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def reverseString(self, s: List[str]) -> None:
"""
Do not return anything, modify s in-place instead.
"""
left, right = 0, len(s) - 1
while(left < right):
s[left], s[right] = s[right], s[left]
left += 1
right -= 1
```
Go Go
```Go ```Go
@ -172,6 +183,26 @@ func reverseString(s []byte) {
} }
``` ```
javaScript:
```js
/**
* @param {character[]} s
* @return {void} Do not return anything, modify s in-place instead.
*/
var reverseString = function(s) {
return s.reverse();
};
var reverseString = function(s) {
let l = -1, r = s.length;
while(++l < --r) [s[l], s[r]] = [s[r], s[l]];
return s;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -162,7 +162,33 @@ class Solution {
Python Python
```python
#时间复杂度O(nlogk)
#空间复杂度O(n)
import heapq
class Solution:
def topKFrequent(self, nums: List[int], k: int) -> List[int]:
#要统计元素出现频率
map_ = {} #nums[i]:对应出现的次数
for i in range(len(nums)):
map_[nums[i]] = map_.get(nums[i], 0) + 1
#对频率排序
#定义一个小顶堆大小为k
pri_que = [] #小顶堆
#用固定大小为k的小顶堆,扫面所有频率的数值
for key, freq in map_.items():
heapq.heappush(pri_que, (freq, key))
if len(pri_que) > k: #如果堆的大小大于了K则队列弹出保证堆的大小一直为k
heapq.heappop(pri_que)
#找出前K个高频元素,因为小顶堆先弹出的是最小的,所以倒叙来输出到数组
result = [0] * k
for i in range(k-1, -1, -1):
result[i] = heapq.heappop(pri_que)[1]
return result
```
Go Go

View File

@ -1,17 +1,18 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 如果哈希值比较少、特别分散、跨度非常大,使用数组就造成空间的极大浪费! > 如果哈希值比较少、特别分散、跨度非常大,使用数组就造成空间的极大浪费!
# 349. 两个数组的交集
## 349. 两个数组的交集
https://leetcode-cn.com/problems/intersection-of-two-arrays/ https://leetcode-cn.com/problems/intersection-of-two-arrays/
@ -23,7 +24,7 @@ https://leetcode-cn.com/problems/intersection-of-two-arrays/
输出结果中的每个元素一定是唯一的。 输出结果中的每个元素一定是唯一的。
我们可以不考虑输出结果的顺序。 我们可以不考虑输出结果的顺序。
# 思路 ## 思路
这道题目主要要学会使用一种哈希数据结构unordered_set这个数据结构可以解决很多类似的问题。 这道题目主要要学会使用一种哈希数据结构unordered_set这个数据结构可以解决很多类似的问题。
@ -31,7 +32,7 @@ https://leetcode-cn.com/problems/intersection-of-two-arrays/
这道题用暴力的解法时间复杂度是O(n^2),那来看看使用哈希法进一步优化。 这道题用暴力的解法时间复杂度是O(n^2),那来看看使用哈希法进一步优化。
那么用数组来做哈希表也是不错的选择,例如[242. 有效的字母异位词](https://mp.weixin.qq.com/s/vM6OszkM6L1Mx2Ralm9Dig)[0383.赎金信](https://mp.weixin.qq.com/s/sYZIR4dFBrw_lr3eJJnteQ) 那么用数组来做哈希表也是不错的选择,例如[242. 有效的字母异位词](https://mp.weixin.qq.com/s/ffS8jaVFNUWyfn_8T31IdA)
但是要注意,**使用数组来做哈希的题目,是因为题目都限制了数值的大小。** 但是要注意,**使用数组来做哈希的题目,是因为题目都限制了数值的大小。**
@ -52,6 +53,7 @@ std::set和std::multiset底层实现都是红黑树std::unordered_set的底
![set哈希法](https://img-blog.csdnimg.cn/2020080918570417.png) ![set哈希法](https://img-blog.csdnimg.cn/2020080918570417.png)
C++代码如下: C++代码如下:
```C++ ```C++
class Solution { class Solution {
public: public:
@ -69,6 +71,13 @@ public:
}; };
``` ```
## 拓展
那有同学可能问了遇到哈希问题我直接都用set不就得了用什么数组啊。
直接使用set 不仅占用空间比数组大而且速度要比数组慢set把数值映射到key上都要做hash计算的。
不要小瞧 这个耗时,在数据量大的情况,差距是很明显的。
## 其他语言版本 ## 其他语言版本
@ -109,11 +118,70 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def intersection(self, nums1: List[int], nums2: List[int]) -> List[int]:
result_set = set()
set1 = set(nums1)
for num in nums2:
if num in set1:
result_set.add(num) # set1里出现的nums2元素 存放到结果
return result_set
```
Go Go
```go
func intersection(nums1 []int, nums2 []int) []int {
m := make(map[int]int)
for _, v := range nums1 {
m[v] = 1
}
var res []int
// 利用count>0实现重复值只拿一次放入返回结果中
for _, v := range nums2 {
if count, ok := m[v]; ok && count > 0 {
res = append(res, v)
m[v]--
}
}
return res
}
```
javaScript:
```js
/**
* @param {number[]} nums1
* @param {number[]} nums2
* @return {number[]}
*/
var intersection = function(nums1, nums2) {
// 根据数组大小交换操作的数组
if(nums1.length < nums2.length) {
const _ = nums1;
nums1 = nums2;
nums2 = _;
}
const nums1Set = new Set(nums1);
const resSet = new Set();
// for(const n of nums2) {
// nums1Set.has(n) && resSet.add(n);
// }
// 循环 比 迭代器快
for(let i = nums2.length - 1; i >= 0; i--) {
nums1Set.has(nums2[i]) && resSet.add(nums2[i]);
}
return Array.from(resSet);
};
```
## 相关题目
* 350.两个数组的交集 II
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 本周讲解了[贪心理论基础](https://mp.weixin.qq.com/s/O935TaoHE9Eexwe_vSbRAg),以及第一道贪心的题目:[贪心算法:分发饼干](https://mp.weixin.qq.com/s/YSuLIAYyRGlyxbp9BNC1uw),可能会给大家一种贪心算法比较简单的错觉,好了,接下来几天的题目难度要上来了,哈哈。 > 本周讲解了[贪心理论基础](https://mp.weixin.qq.com/s/O935TaoHE9Eexwe_vSbRAg),以及第一道贪心的题目:[贪心算法:分发饼干](https://mp.weixin.qq.com/s/YSuLIAYyRGlyxbp9BNC1uw),可能会给大家一种贪心算法比较简单的错觉,好了,接下来几天的题目难度要上来了,哈哈。
@ -138,12 +138,38 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def wiggleMaxLength(self, nums: List[int]) -> int:
preC,curC,res = 0,0,1 #题目里nums长度大于等于1当长度为1时其实到不了for循环里去所以不用考虑nums长度
for i in range(len(nums) - 1):
curC = nums[i + 1] - nums[i]
if curC * preC <= 0 and curC !=0: #差值为0时,不算摆动
res += 1
preC = curC #如果当前差值和上一个差值为一正一负时,才需要用当前差值替代上一个差值
return res
```
Go Go
Javascript:
```Javascript
var wiggleMaxLength = function(nums) {
if(nums.length <= 1) return nums.length
let result = 1
let preDiff = 0
let curDiff = 0
for(let i = 0; i <= nums.length; i++) {
curDiff = nums[i + 1] - nums[i]
if((curDiff > 0 && preDiff <= 0) || (curDiff < 0 && preDiff >= 0)) {
result++
preDiff = curDiff
}
}
return result
};
```
----------------------- -----------------------
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 动态规划Carl称它为排列总和 # 动态规划Carl称它为排列总和
## 377. 组合总和 Ⅳ ## 377. 组合总和 Ⅳ
@ -163,7 +163,7 @@ class Solution {
return dp[target]; return dp[target];
} }
} }
```
Python Python
@ -183,7 +183,23 @@ class Solution:
Go Go
```go
func combinationSum4(nums []int, target int) int {
//定义dp数组
dp := make([]int, target+1)
// 初始化
dp[0] = 1
// 遍历顺序, 先遍历背包,再循环遍历物品
for j:=0;j<=target;j++ {
for i:=0 ;i < len(nums);i++ {
if j >= nums[i] {
dp[j] += dp[j-nums[i]]
}
}
}
return dp[target]
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -26,9 +26,9 @@ canConstruct("a", "b") -> false
canConstruct("aa", "ab") -> false canConstruct("aa", "ab") -> false
canConstruct("aa", "aab") -> true canConstruct("aa", "aab") -> true
# 思路 ## 思路
这道题目和[242.有效的字母异位词](https://mp.weixin.qq.com/s/vM6OszkM6L1Mx2Ralm9Dig)很像,[242.有效的字母异位词](https://mp.weixin.qq.com/s/vM6OszkM6L1Mx2Ralm9Dig)相当于求 字符串a 和 字符串b 是否可以相互组成 ,而这道题目是求 字符串a能否组成字符串b而不用管字符串b 能不能组成字符串a。 这道题目和[242.有效的字母异位词](https://mp.weixin.qq.com/s/ffS8jaVFNUWyfn_8T31IdA)很像,[242.有效的字母异位词](https://mp.weixin.qq.com/s/ffS8jaVFNUWyfn_8T31IdA)相当于求 字符串a 和 字符串b 是否可以相互组成 ,而这道题目是求 字符串a能否组成字符串b而不用管字符串b 能不能组成字符串a。
本题判断第一个字符串ransom能不能由第二个字符串magazines里面的字符构成但是这里需要注意两点。 本题判断第一个字符串ransom能不能由第二个字符串magazines里面的字符构成但是这里需要注意两点。
@ -36,7 +36,7 @@ canConstruct("aa", "aab") -> true
* 第二点 “你可以假设两个字符串均只含有小写字母。” *说明只有小写字母*,这一点很重要 * 第二点 “你可以假设两个字符串均只含有小写字母。” *说明只有小写字母*,这一点很重要
# 暴力解法 ## 暴力解法
那么第一个思路其实就是暴力枚举了两层for循环不断去寻找代码如下 那么第一个思路其实就是暴力枚举了两层for循环不断去寻找代码如下
@ -67,7 +67,7 @@ public:
这里时间复杂度是比较高的而且里面还有一个字符串删除也就是erase的操作也是费时的当然这段代码也可以过这道题。 这里时间复杂度是比较高的而且里面还有一个字符串删除也就是erase的操作也是费时的当然这段代码也可以过这道题。
# 哈希解法 ## 哈希解法
因为题目所只有小写字母,那可以采用空间换取时间的哈希策略, 用一个长度为26的数组还记录magazine里字母出现的次数。 因为题目所只有小写字母,那可以采用空间换取时间的哈希策略, 用一个长度为26的数组还记录magazine里字母出现的次数。
@ -75,7 +75,7 @@ public:
依然是数组在哈希法中的应用。 依然是数组在哈希法中的应用。
一些同学可能想用数组干啥都用map完事了**其实在本题的情况下使用map的空间消耗要比数组大一些的因为map要维护红黑树或者哈希表而且还要做哈希函数。 所以数组更加简单直接有效!** 一些同学可能想用数组干啥都用map完事了**其实在本题的情况下使用map的空间消耗要比数组大一些的因为map要维护红黑树或者哈希表而且还要做哈希函数,是费时的!数据量大的话就能体现出来差别了。 所以数组更加简单直接有效!**
代码如下: 代码如下:
@ -105,8 +105,6 @@ public:
## 其他语言版本 ## 其他语言版本
@ -138,10 +136,74 @@ class Solution {
``` ```
Python Python
```py
class Solution(object):
def canConstruct(self, ransomNote, magazine):
"""
:type ransomNote: str
:type magazine: str
:rtype: bool
"""
# use a dict to store the number of letter occurance in ransomNote
hashmap = dict()
for s in ransomNote:
if s in hashmap:
hashmap[s] += 1
else:
hashmap[s] = 1
# check if the letter we need can be found in magazine
for l in magazine:
if l in hashmap:
hashmap[l] -= 1
for key in hashmap:
if hashmap[key] > 0:
return False
return True
```
Go Go
```go
func canConstruct(ransomNote string, magazine string) bool {
record := make([]int, 26)
for _, v := range magazine {
record[v-'a']++
}
for _, v := range ransomNote {
record[v-'a']--
if record[v-'a'] < 0 {
return false
}
}
return true
}
```
javaScript:
```js
/**
* @param {string} ransomNote
* @param {string} magazine
* @return {boolean}
*/
var canConstruct = function(ransomNote, magazine) {
const strArr = new Array(26).fill(0),
base = "a".charCodeAt();
for(const s of magazine) {
strArr[s.charCodeAt() - base]++;
}
for(const s of ransomNote) {
const index = s.charCodeAt() - base;
if(!strArr[index]) return false;
strArr[index]--;
}
return true;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 392.判断子序列 ## 392.判断子序列
@ -144,7 +144,20 @@ Java
Python Python
```python
class Solution:
def isSubsequence(self, s: str, t: str) -> bool:
dp = [[0] * (len(t)+1) for _ in range(len(s)+1)]
for i in range(1, len(s)+1):
for j in range(1, len(t)+1):
if s[i-1] == t[j-1]:
dp[i][j] = dp[i-1][j-1] + 1
else:
dp[i][j] = dp[i][j-1]
if dp[-1][-1] == len(s):
return True
return False
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 404.左叶子之和 ## 404.左叶子之和
@ -205,10 +205,139 @@ class Solution {
Python Python
```Python
**递归**
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
class Solution:
def sumOfLeftLeaves(self, root: TreeNode) -> int:
self.res=0
def areleftleaves(root):
if not root:return
if root.left and (not root.left.left) and (not root.left.right):self.res+=root.left.val
areleftleaves(root.left)
areleftleaves(root.right)
areleftleaves(root)
return self.res
```
Go Go
> 递归法
```go
/**
* Definition for a binary tree node.
* type TreeNode struct {
* Val int
* Left *TreeNode
* Right *TreeNode
* }
*/
func sumOfLeftLeaves(root *TreeNode) int {
var res int
findLeft(root,&res)
return res
}
func findLeft(root *TreeNode,res *int){
//左节点
if root.Left!=nil&&root.Left.Left==nil&&root.Left.Right==nil{
*res=*res+root.Left.Val
}
if root.Left!=nil{
findLeft(root.Left,res)
}
if root.Right!=nil{
findLeft(root.Right,res)
}
}
```
> 迭代法
```go
/**
* Definition for a binary tree node.
* type TreeNode struct {
* Val int
* Left *TreeNode
* Right *TreeNode
* }
*/
func sumOfLeftLeaves(root *TreeNode) int {
var res int
queue:=list.New()
queue.PushBack(root)
for queue.Len()>0{
length:=queue.Len()
for i:=0;i<length;i++{
node:=queue.Remove(queue.Front()).(*TreeNode)
if node.Left!=nil&&node.Left.Left==nil&&node.Left.Right==nil{
res=res+node.Left.Val
}
if node.Left!=nil{
queue.PushBack(node.Left)
}
if node.Right!=nil{
queue.PushBack(node.Right)
}
}
}
return res
}
```
JavaScript:
递归版本
```javascript
var sumOfLeftLeaves = function(root) {
//采用后序遍历 递归遍历
// 1. 确定递归函数参数
const nodesSum = function(node){
// 2. 确定终止条件
if(node===null){
return 0;
}
let leftValue = sumOfLeftLeaves(node.left);
let rightValue = sumOfLeftLeaves(node.right);
// 3. 单层递归逻辑
let midValue = 0;
if(node.left&&node.left.left===null&&node.left.right===null){
midValue = node.left.val;
}
let sum = midValue + leftValue + rightValue;
return sum;
}
return nodesSum(root);
};
```
迭代版本
```javascript
var sumOfLeftLeaves = function(root) {
//采用层序遍历
if(root===null){
return null;
}
let queue = [];
let sum = 0;
queue.push(root);
while(queue.length){
let node = queue.shift();
if(node.left!==null&&node.left.left===null&&node.left.right===null){
sum+=node.left.val;
}
node.left&&queue.push(node.left);
node.right&&queue.push(node.right);
}
return sum;
};
```
@ -216,6 +345,4 @@ Go
* 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw) * 作者微信:[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)
* B站视频[代码随想录](https://space.bilibili.com/525438321) * B站视频[代码随想录](https://space.bilibili.com/525438321)
* 知识星球:[代码随想录](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ) * 知识星球:[代码随想录](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ)
<div align="center"><img src=../pics/公众号.png width=450 alt=> </img></div> <div align="center"><img src=../pics/公众号.png width=450 alt=> </img></div>

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 406.根据身高重建队列 ## 406.根据身高重建队列
@ -211,11 +211,40 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def reconstructQueue(self, people: List[List[int]]) -> List[List[int]]:
people.sort(key=lambda x: (x[0], -x[1]), reverse=True)
que = []
for p in people:
if p[1] > len(que):
que.append(p)
else:
que.insert(p[1], p)
return que
```
Go Go
Javascript:
```Javascript
var reconstructQueue = function(people) {
let queue = []
people.sort((a, b ) => {
if(b[0] !== a[0]) {
return b[0] - a[0]
} else {
return a[1] - b[1]
}
})
for(let i = 0; i < people.length; i++) {
queue.splice(people[i][1], 0, people[i])
}
return queue
};
```
----------------------- -----------------------

View File

@ -1,11 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 动态规划分割等和子集可以用01背包
## 416. 分割等和子集 ## 416. 分割等和子集
@ -29,6 +28,10 @@
输出: false 输出: false
解释: 数组不能分割成两个元素和相等的子集. 解释: 数组不能分割成两个元素和相等的子集.
提示:
* 1 <= nums.length <= 200
* 1 <= nums[i] <= 100
## 思路 ## 思路
这道题目初步看,是如下两题几乎是一样的,大家可以用回溯法,解决如下两题 这道题目初步看,是如下两题几乎是一样的,大家可以用回溯法,解决如下两题
@ -174,7 +177,7 @@ public:
这道题目就是一道01背包应用类的题目需要我们拆解题目然后套入01背包的场景。 这道题目就是一道01背包应用类的题目需要我们拆解题目然后套入01背包的场景。
01背包相对于本题主要要理解题目中物品是nums[i]重量是nums[i]i价值也是nums[i]背包体积是sum/2。 01背包相对于本题主要要理解题目中物品是nums[i]重量是nums[i]价值也是nums[i]背包体积是sum/2。
看代码的话就可以发现基本就是按照01背包的写法来的。 看代码的话就可以发现基本就是按照01背包的写法来的。
@ -222,8 +225,18 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def canPartition(self, nums: List[int]) -> bool:
taraget = sum(nums)
if taraget % 2 == 1: return False
taraget //= 2
dp = [0] * 10001
for i in range(len(nums)):
for j in range(taraget, nums[i] - 1, -1):
dp[j] = max(dp[j], dp[j - nums[i]] + nums[i])
return taraget == dp[taraget]
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 435. 无重叠区间 ## 435. 无重叠区间
@ -212,7 +212,19 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def eraseOverlapIntervals(self, intervals: List[List[int]]) -> int:
if len(intervals) == 0: return 0
intervals.sort(key=lambda x: x[1])
count = 1 # 记录非交叉区间的个数
end = intervals[0][1] # 记录区间分割点
for i in range(1, len(intervals)):
if end <= intervals[i][0]:
count += 1
end = intervals[i][1]
return len(intervals) - count
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 二叉搜索树删除节点就涉及到结构调整了 > 二叉搜索树删除节点就涉及到结构调整了
@ -281,7 +281,43 @@ class Solution {
``` ```
Python Python
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
class Solution:
def deleteNode(self, root: TreeNode, key: int) -> TreeNode:
if not root: return root #第一种情况:没找到删除的节点,遍历到空节点直接返回了
if root.val == key:
if not root.left and not root.right: #第二种情况:左右孩子都为空(叶子节点),直接删除节点, 返回NULL为根节点
del root
return None
if not root.left and root.right: #第三种情况:其左孩子为空,右孩子不为空,删除节点,右孩子补位 ,返回右孩子为根节点
tmp = root
root = root.right
del tmp
return root
if root.left and not root.right: #第四种情况:其右孩子为空,左孩子不为空,删除节点,左孩子补位,返回左孩子为根节点
tmp = root
root = root.left
del tmp
return root
else: #第五种情况:左右孩子节点都不为空,则将删除节点的左子树放到删除节点的右子树的最左面节点的左孩子的位置
v = root.right
while v.left:
v = v.left
v.left = root.left
tmp = root
root = root.right
del tmp
return root
if root.val > key: root.left = self.deleteNode(root.left,key) #左递归
if root.val < key: root.right = self.deleteNode(root.right,key) #右递归
return root
```
Go Go
```Go ```Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 452. 用最少数量的箭引爆气球 ## 452. 用最少数量的箭引爆气球
@ -70,7 +70,7 @@
其实都可以!只不过对应的遍历顺序不同,我就按照气球的起始位置排序了。 其实都可以!只不过对应的遍历顺序不同,我就按照气球的起始位置排序了。
既然按照其实位置排序,那么就从前向后遍历气球数组,靠左尽可能让气球重复。 既然按照起始位置排序,那么就从前向后遍历气球数组,靠左尽可能让气球重复。
从前向后遍历遇到重叠的气球了怎么办? 从前向后遍历遇到重叠的气球了怎么办?
@ -142,16 +142,8 @@ Java
```java ```java
class Solution { class Solution {
public int findMinArrowShots(int[][] points) { public int findMinArrowShots(int[][] points) {
Arrays.sort(points, new Comparator<int[]>() { if (points.length == 0) return 0;
@Override Arrays.sort(points, (o1, o2) -> Integer.compare(o1[0], o2[0]));
public int compare(int[] o1, int[] o2) {
if (o1[0] != o2[0]) {
return Integer.compare(o1[0],o2[0]);
} else {
return Integer.compare(o1[0],o2[0]);
}
}
});
int count = 1; int count = 1;
for (int i = 1; i < points.length; i++) { for (int i = 1; i < points.length; i++) {
@ -167,11 +159,40 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def findMinArrowShots(self, points: List[List[int]]) -> int:
if len(points) == 0: return 0
points.sort(key=lambda x: x[0])
result = 1
for i in range(1, len(points)):
if points[i][0] > points[i - 1][1]: # 气球i和气球i-1不挨着注意这里不是>=
result += 1
else:
points[i][1] = min(points[i - 1][1], points[i][1]) # 更新重叠气球最小右边界
return result
```
Go Go
Javascript:
```Javascript
var findMinArrowShots = function(points) {
points.sort((a, b) => {
return a[0] - b[0]
})
let result = 1
for(let i = 1; i < points.length; i++) {
if(points[i][0] > points[i - 1][1]) {
result++
} else {
points[i][1] = Math.min(points[i - 1][1], points[i][1])
}
}
return result
};
```
----------------------- -----------------------

View File

@ -1,16 +1,17 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 需要哈希的地方都能找到map的身影 > 需要哈希的地方都能找到map的身影
# 第454题.四数相加II # 第454题.四数相加II
https://leetcode-cn.com/problems/4sum-ii/ https://leetcode-cn.com/problems/4sum-ii/
给定四个包含整数的数组列表 A , B , C , D ,计算有多少个元组 (i, j, k, l) 使得 A[i] + B[j] + C[k] + D[l] = 0。 给定四个包含整数的数组列表 A , B , C , D ,计算有多少个元组 (i, j, k, l) 使得 A[i] + B[j] + C[k] + D[l] = 0。
@ -24,10 +25,8 @@ A = [ 1, 2]
B = [-2,-1] B = [-2,-1]
C = [-1, 2] C = [-1, 2]
D = [ 0, 2] D = [ 0, 2]
输出: 输出:
2 2
**解释:** **解释:**
两个元组如下: 两个元组如下:
1. (0, 0, 0, 1) -> A[0] + B[0] + C[0] + D[1] = 1 + (-2) + (-1) + 2 = 0 1. (0, 0, 0, 1) -> A[0] + B[0] + C[0] + D[1] = 1 + (-2) + (-1) + 2 = 0
@ -121,8 +120,88 @@ class Solution {
Python Python
```
class Solution(object):
def fourSumCount(self, nums1, nums2, nums3, nums4):
"""
:type nums1: List[int]
:type nums2: List[int]
:type nums3: List[int]
:type nums4: List[int]
:rtype: int
"""
# use a dict to store the elements in nums1 and nums2 and their sum
hashmap = dict()
for n1 in nums1:
for n2 in nums2:
if n1 + n2 in hashmap:
hashmap[n1+n2] += 1
else:
hashmap[n1+n2] = 1
# if the -(a+b) exists in nums3 and nums4, we shall add the count
count = 0
for n3 in nums3:
for n4 in nums4:
key = - n3 - n4
if key in hashmap:
count += hashmap[key]
return count
```
Go Go
```go
func fourSumCount(nums1 []int, nums2 []int, nums3 []int, nums4 []int) int {
m := make(map[int]int)
count := 0
for _, v1 := range nums1 {
for _, v2 := range nums2 {
m[v1+v2]++
}
}
for _, v3 := range nums3 {
for _, v4 := range nums4 {
count += m[-v3-v4]
}
}
return count
}
```
javaScript:
```js
/**
* @param {number[]} nums1
* @param {number[]} nums2
* @param {number[]} nums3
* @param {number[]} nums4
* @return {number}
*/
var fourSumCount = function(nums1, nums2, nums3, nums4) {
const twoSumMap = new Map();
let count = 0;
for(const n1 of nums1) {
for(const n2 of nums2) {
const sum = n1 + n2;
twoSumMap.set(sum, (twoSumMap.get(sum) || 0) + 1)
}
}
for(const n3 of nums3) {
for(const n4 of nums4) {
const sum = n3 + n4;
count += (twoSumMap.get(0 - sum) || 0)
}
}
return count;
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 455.分发饼干 ## 455.分发饼干
@ -134,11 +134,37 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def findContentChildren(self, g: List[int], s: List[int]) -> int:
g.sort()
s.sort()
res = 0
for i in range(len(s)):
if res <len(g) and s[i] >= g[res]: #小饼干先喂饱小胃口
res += 1
return res
```
Go Go
Javascript:
```Javascript
var findContentChildren = function(g, s) {
g = g.sort((a, b) => a - b)
s = s.sort((a, b) => a - b)
let result = 0
let index = s.length - 1
for(let i = g.length - 1; i >= 0; i--) {
if(index >= 0 && s[index] >= g[i]) {
result++
index--
}
}
return result
};
```
----------------------- -----------------------

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
@ -149,15 +149,151 @@ public:
## 其他语言版本 ## 其他语言版本
Java Java
```java
class Solution {
public boolean repeatedSubstringPattern(String s) {
if (s.equals("")) return false;
int len = s.length();
// 原串加个空格(哨兵)使下标从1开始这样j从0开始也不用初始化了
s = " " + s;
char[] chars = s.toCharArray();
int[] next = new int[len + 1];
// 构造 next 数组过程j从0开始(空格)i从2开始
for (int i = 2, j = 0; i <= len; i++) {
// 匹配不成功j回到前一位置 next 数组所对应的值
while (j > 0 && chars[i] != chars[j + 1]) j = next[j];
// 匹配成功j往后移
if (chars[i] == chars[j + 1]) j++;
// 更新 next 数组的值
next[i] = j;
}
// 最后判断是否是重复的子字符串,这里 next[len] 即代表next数组末尾的值
if (next[len] > 0 && len % (len - next[len]) == 0) {
return true;
}
return false;
}
}
```
Python Python
这里使用了前缀表统一减一的实现方式
```python
class Solution:
def repeatedSubstringPattern(self, s: str) -> bool:
if len(s) == 0:
return False
nxt = [0] * len(s)
self.getNext(nxt, s)
if nxt[-1] != -1 and len(s) % (len(s) - (nxt[-1] + 1)) == 0:
return True
return False
def getNext(self, nxt, s):
nxt[0] = -1
j = -1
for i in range(1, len(s)):
while j >= 0 and s[i] != s[j+1]:
j = nxt[j]
if s[i] == s[j+1]:
j += 1
nxt[i] = j
return nxt
```
前缀表(不减一)的代码实现
```python
class Solution:
def repeatedSubstringPattern(self, s: str) -> bool:
if len(s) == 0:
return False
nxt = [0] * len(s)
self.getNext(nxt, s)
if nxt[-1] != 0 and len(s) % (len(s) - nxt[-1]) == 0:
return True
return False
def getNext(self, nxt, s):
nxt[0] = 0
j = 0
for i in range(1, len(s)):
while j > 0 and s[i] != s[j]:
j = nxt[j - 1]
if s[i] == s[j]:
j += 1
nxt[i] = j
return nxt
```
Go Go
这里使用了前缀表统一减一的实现方式
```go
func repeatedSubstringPattern(s string) bool {
n := len(s)
if n == 0 {
return false
}
next := make([]int, n)
j := -1
next[0] = j
for i := 1; i < n; i++ {
for j >= 0 && s[i] != s[j+1] {
j = next[j]
}
if s[i] == s[j+1] {
j++
}
next[i] = j
}
// next[n-1]+1 最长相同前后缀的长度
if next[n-1] != -1 && n%(n-(next[n-1]+1)) == 0 {
return true
}
return false
}
```
前缀表(不减一)的代码实现
```go
func repeatedSubstringPattern(s string) bool {
n := len(s)
if n == 0 {
return false
}
j := 0
next := make([]int, n)
next[0] = j
for i := 1; i < n; i++ {
for j > 0 && s[i] != s[j] {
j = next[j-1]
}
if s[i] == s[j] {
j++
}
next[i] = j
}
// next[n-1] 最长相同前后缀的长度
if next[n-1] != 0 && n%(n-next[n-1]) == 0 {
return true
}
return false
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 动态规划:一和零! # 动态规划:一和零!
## 474.一和零 ## 474.一和零
@ -190,10 +190,59 @@ class Solution {
``` ```
Python Python
```python3
class Solution:
def findMaxForm(self, strs: List[str], m: int, n: int) -> int:
dp = [[0] * (n + 1) for _ in range(m + 1)] # 默认初始化0
# 遍历物品
for str in strs:
ones = str.count('1')
zeros = str.count('0')
# 遍历背包容量且从后向前遍历!
for i in range(m, zeros - 1, -1):
for j in range(n, ones - 1, -1):
dp[i][j] = max(dp[i][j], dp[i - zeros][j - ones] + 1)
return dp[m][n]
```
Go Go
```go
func findMaxForm(strs []string, m int, n int) int {
// 定义数组
dp := make([][]int, m+1)
for i,_ := range dp {
dp[i] = make([]int, n+1 )
}
// 遍历
for i:=0;i<len(strs);i++ {
zeroNum,oneNum := 0 , 0
//计算0,1 个数
//或者直接strings.Count(strs[i],"0")
for _,v := range strs[i] {
if v == '0' {
zeroNum++
}
}
oneNum = len(strs[i])-zeroNum
// 从后往前 遍历背包容量
for j:= m ; j >= zeroNum;j-- {
for k:=n ; k >= oneNum;k-- {
// 推导公式
dp[j][k] = max(dp[j][k],dp[j-zeroNum][k-oneNum]+1)
}
}
//fmt.Println(dp)
}
return dp[m][n]
}
func max(a,b int) int {
if a > b {
return a
}
return b
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 和子集问题有点像,但又处处是陷阱 > 和子集问题有点像,但又处处是陷阱
@ -229,10 +229,59 @@ class Solution {
Python Python
```python3
class Solution:
def findSubsequences(self, nums: List[int]) -> List[List[int]]:
res = []
path = []
def backtrack(nums,startIndex):
repeat = [] #这里使用数组来进行去重操作
if len(path) >=2:
res.append(path[:]) #注意这里不要加return,要取树上的节点
for i in range(startIndex,len(nums)):
if nums[i] in repeat:
continue
if len(path) >= 1:
if nums[i] < path[-1]:
continue
repeat.append(nums[i]) #记录这个元素在本层用过了,本层后面不能再用了
path.append(nums[i])
backtrack(nums,i+1)
path.pop()
backtrack(nums,0)
return res
```
Go Go
Javascript:
```Javascript
var findSubsequences = function(nums) {
let result = []
let path = []
function backtracing(startIndex) {
if(path.length > 1) {
result.push(path.slice())
}
let uset = []
for(let i = startIndex; i < nums.length; i++) {
if((path.length > 0 && nums[i] < path[path.length - 1]) || uset[nums[i] + 100]) {
continue
}
uset[nums[i] + 100] = true
path.push(nums[i])
backtracing(i + 1)
path.pop()
}
}
backtracing(0)
return result
};
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
# 动态规划:目标和! # 动态规划:目标和!
## 494. 目标和 ## 494. 目标和
@ -21,8 +21,8 @@
输入nums: [1, 1, 1, 1, 1], S: 3 输入nums: [1, 1, 1, 1, 1], S: 3
输出5 输出5
解释:
解释:
-1+1+1+1+1 = 3 -1+1+1+1+1 = 3
+1-1+1+1+1 = 3 +1-1+1+1+1 = 3
+1+1-1+1+1 = 3 +1+1-1+1+1 = 3
@ -150,7 +150,7 @@ dp[j] 表示填满j包括j这么大容积的包有dp[i]种方法
有哪些来源可以推出dp[j]呢? 有哪些来源可以推出dp[j]呢?
不考虑nums[i]的情况下填满容量为j - nums[i]的背包有dp[j - nums[i]]方法。 不考虑nums[i]的情况下填满容量为j - nums[i]的背包有dp[j - nums[i]]方法。
那么只要搞到nums[i]的话凑成dp[j]就有dp[j - nums[i]] 种方法。 那么只要搞到nums[i]的话凑成dp[j]就有dp[j - nums[i]] 种方法。
@ -225,7 +225,7 @@ public:
是的如果仅仅是求个数的话就可以用dp但[回溯算法39. 组合总和](https://mp.weixin.qq.com/s/FLg8G6EjVcxBjwCbzpACPw)要求的是把所有组合列出来,还是要使用回溯法爆搜的。 是的如果仅仅是求个数的话就可以用dp但[回溯算法39. 组合总和](https://mp.weixin.qq.com/s/FLg8G6EjVcxBjwCbzpACPw)要求的是把所有组合列出来,还是要使用回溯法爆搜的。
还是有点难度,大家也可以记住,在求装满背包有几种方法的情况下,递推公式一般为: 还是有点难度,大家也可以记住,在求装满背包有几种方法的情况下,递推公式一般为:
``` ```
dp[j] += dp[j - nums[i]]; dp[j] += dp[j - nums[i]];
@ -261,10 +261,50 @@ class Solution {
``` ```
Python Python
```python
class Solution:
def findTargetSumWays(self, nums: List[int], target: int) -> int:
sumValue = sum(nums)
if target > sumValue or (sumValue + target) % 2 == 1: return 0
bagSize = (sumValue + target) // 2
dp = [0] * (bagSize + 1)
dp[0] = 1
for i in range(len(nums)):
for j in range(bagSize, nums[i] - 1, -1):
dp[j] += dp[j - nums[i]]
return dp[bagSize]
```
Go Go
```go
func findTargetSumWays(nums []int, target int) int {
sum := 0
for _, v := range nums {
sum += v
}
if target > sum {
return 0
}
if (sum+target)%2 == 1 {
return 0
}
// 计算背包大小
bag := (sum + target) / 2
// 定义dp数组
dp := make([]int, bag+1)
// 初始化
dp[0] = 1
// 遍历顺序
for i := 0; i < len(nums); i++ {
for j := bag; j >= nums[i]; j-- {
//推导公式
dp[j] += dp[j-nums[i]]
//fmt.Println(dp)
}
}
return dp[bag]
}
```

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
> 二叉树上应该怎么求,二叉搜索树上又应该怎么求? > 二叉树上应该怎么求,二叉搜索树上又应该怎么求?
@ -394,8 +394,39 @@ class Solution {
``` ```
Python Python
```python
# Definition for a binary tree node.
# class TreeNode:
# def __init__(self, val=0, left=None, right=None):
# self.val = val
# self.left = left
# self.right = right
//递归法
class Solution:
def findMode(self, root: TreeNode) -> List[int]:
if not root: return
self.pre = root
self.count = 0 //统计频率
self.countMax = 0 //最大频率
self.res = []
def findNumber(root):
if not root: return None // 第一个节点
findNumber(root.left) //左
if self.pre.val == root.val: //中: 与前一个节点数值相同
self.count += 1
else: // 与前一个节点数值不同
self.pre = root
self.count = 1
if self.count > self.countMax: // 如果计数大于最大值频率
self.countMax = self.count // 更新最大频率
self.res = [root.val] //更新res
elif self.count == self.countMax: // 如果和最大值相同放进res中
self.res.append(root.val)
findNumber(root.right) //右
return
findNumber(root)
return self.res
```
Go Go

View File

@ -1,10 +1,10 @@
<p align="center"> <p align="center">
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a> <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
<a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a> <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
<a href="https://img-blog.csdnimg.cn/20201210231711160.png"><img src="https://img.shields.io/badge/公众号-代码随想录-brightgreen" alt=""></a>
<a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a> <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
<a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p> </p>
<p align="center"><strong>欢迎大家参与本项目,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p> <p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>,贡献其他语言版本的代码,拥抱开源,让更多学习算法的小伙伴们收益!</strong></p>
## 509. 斐波那契数 ## 509. 斐波那契数
@ -171,12 +171,55 @@ public:
Java Java
```Java
class Solution {
public int fib(int n) {
if (n < 2) return n;
int a = 0, b = 1, c = 0;
for (int i = 1; i < n; i++) {
c = a + b;
a = b;
b = c;
}
return c;
}
}
```
Python Python
```python3
class Solution:
def fib(self, n: int) -> int:
if n < 2:
return n
a, b, c = 0, 1, 0
for i in range(1, n):
c = a + b
a, b = b, c
return c
# 递归实现
class Solution:
def fib(self, n: int) -> int:
if n < 2:
return n
return self.fib(n - 1) + self.fib(n - 2)
```
Go Go
```Go
func fib(n int) int {
if n < 2 {
return n
}
a, b, c := 0, 1, 0
for i := 1; i < n; i++ {
c = a + b
a, b = b, c
}
return c
}
```

Some files were not shown because too many files have changed in this diff Show More