From 97cd84d47870a8ab2aad30838b9ebc1a9a450099 Mon Sep 17 00:00:00 2001 From: zcxzcxzcx <18810692826@163.com> Date: Sun, 2 Jan 2022 22:16:26 +0800 Subject: [PATCH 01/44] =?UTF-8?q?Create=200093.=E5=A4=8D=E5=8E=9FIP?= =?UTF-8?q?=E5=9C=B0=E5=9D=80.md?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 优化时间复杂度,更好地剪枝(java版本) --- problems/0093.复原IP地址.md | 42 +++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/problems/0093.复原IP地址.md b/problems/0093.复原IP地址.md index 3e7cd1ad..67bb1bbe 100644 --- a/problems/0093.复原IP地址.md +++ b/problems/0093.复原IP地址.md @@ -304,6 +304,48 @@ class Solution { return true; } } + +//方法二:比上面的方法时间复杂度低,更好地剪枝,优化时间复杂度 +class Solution { + List result = new ArrayList(); + StringBuilder stringBuilder = new StringBuilder(); + + public List restoreIpAddresses(String s) { + restoreIpAddressesHandler(s, 0, 0); + return result; + } + + // number表示stringbuilder中ip段的数量 + public void restoreIpAddressesHandler(String s, int start, int number) { + // 如果start等于s的长度并且ip段的数量是4,则加入结果集,并返回 + if (start == s.length() && number == 4) { + result.add(stringBuilder.toString()); + return; + } + // 如果start等于s的长度但是ip段的数量不为4,或者ip段的数量为4但是start小于s的长度,则直接返回 + if (start == s.length() || number == 4) { + return; + } + // 剪枝:ip段的长度最大是3,并且ip段处于[0,255] + for (int i = start; i < s.length() && i - start < 3 && Integer.parseInt(s.substring(start, i + 1)) >= 0 + && Integer.parseInt(s.substring(start, i + 1)) <= 255; i++) { + // 如果ip段的长度大于1,并且第一位为0的话,continue + if (i + 1 - start > 1 && s.charAt(start) - '0' == 0) { + continue; + } + stringBuilder.append(s.substring(start, i + 1)); + // 当stringBuilder里的网段数量小于3时,才会加点;如果等于3,说明已经有3段了,最后一段不需要再加点 + if (number < 3) { + stringBuilder.append("."); + } + number++; + restoreIpAddressesHandler(s, i + 1, number); + number--; + // 删除当前stringBuilder最后一个网段,注意考虑点的数量的问题 + stringBuilder.delete(start + number, i + number + 2); + } + } +} ``` ## python From 8ce87963e5fe7e74657109d71c80ce3ce3b07da6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9E=81=E5=AE=A2=E5=AD=A6=E4=BC=9F?= Date: Mon, 7 Feb 2022 13:29:05 +0800 Subject: [PATCH 02/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=20=E4=BA=8C=E5=8F=89?= =?UTF-8?q?=E6=A0=91=EF=BC=9A=E4=BB=A5=E4=B8=BA=E4=BD=BF=E7=94=A8=E4=BA=86?= =?UTF-8?q?=E9=80=92=E5=BD=92=EF=BC=8C=E5=85=B6=E5=AE=9E=E8=BF=98=E9=9A=90?= =?UTF-8?q?=E8=97=8F=E7=9D=80=E5=9B=9E=E6=BA=AF=20Swift=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/二叉树中递归带着回溯.md | 55 ++++++++++++++++++++++ 1 file changed, 55 insertions(+) diff --git a/problems/二叉树中递归带着回溯.md b/problems/二叉树中递归带着回溯.md index 20b87f87..603854dc 100644 --- a/problems/二叉树中递归带着回溯.md +++ b/problems/二叉树中递归带着回溯.md @@ -515,6 +515,61 @@ var binaryTreePaths = function(root) { }; ``` +Swift: +> 100.相同的树 +```swift +// 递归 +func isSameTree(_ p: TreeNode?, _ q: TreeNode?) -> Bool { + return _isSameTree3(p, q) +} +func _isSameTree3(_ p: TreeNode?, _ q: TreeNode?) -> Bool { + if p == nil && q == nil { + return true + } else if p == nil && q != nil { + return false + } else if p != nil && q == nil { + return false + } else if p!.val != q!.val { + return false + } + let leftSide = _isSameTree3(p!.left, q!.left) + let rightSide = _isSameTree3(p!.right, q!.right) + return leftSide && rightSide +} +``` + +> 257.二叉树的不同路径 +```swift +// 递归/回溯 +func binaryTreePaths(_ root: TreeNode?) -> [String] { + var res = [String]() + guard let root = root else { + return res + } + var paths = [Int]() + _binaryTreePaths3(root, res: &res, paths: &paths) + return res +} +func _binaryTreePaths3(_ root: TreeNode, res: inout [String], paths: inout [Int]) { + paths.append(root.val) + if root.left == nil && root.right == nil { + var str = "" + for i in 0 ..< (paths.count - 1) { + str.append("\(paths[i])->") + } + str.append("\(paths.last!)") + res.append(str) + } + if let left = root.left { + _binaryTreePaths3(left, res: &res, paths: &paths) + paths.removeLast() + } + if let right = root.right { + _binaryTreePaths3(right, res: &res, paths: &paths) + paths.removeLast() + } +} +``` -----------------------
From 3aa54bfb8a8604a8cfb05a4fa8c606ebe6b09db3 Mon Sep 17 00:00:00 2001 From: Wayne <3522373084@qq.com> Date: Mon, 7 Feb 2022 21:39:51 +0800 Subject: [PATCH 03/44] =?UTF-8?q?343=E6=95=B4=E6=95=B0=E6=8B=86=E5=88=86,?= =?UTF-8?q?=E6=9B=B4=E6=96=B0=E7=AC=AC=E4=BA=8C=E5=B1=82=E5=BE=AA=E7=8E=AF?= =?UTF-8?q?=20j=20=E7=9A=84=E8=8C=83=E5=9B=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0343.整数拆分.md | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-) diff --git a/problems/0343.整数拆分.md b/problems/0343.整数拆分.md index 5d11f670..f616a606 100644 --- a/problems/0343.整数拆分.md +++ b/problems/0343.整数拆分.md @@ -197,14 +197,17 @@ 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])); + //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-j;j++){ + // 这里的 j 其实最大值为 i-j,再大只不过是重复而已, + //并且,在本题中,我们分析 dp[0], dp[1]都是无意义的, + //j 最大到 i-j,就不会用到 dp[0]与dp[1] + dp[i]=Math.max(dp[i],Math.max(j*(i-j),j*dp[i-j])); + // j * (i - j) 是单纯的把整数 i 拆分为两个数 也就是 i,i-j ,再相乘 + //而j * dp[i - j]是将 i 拆分成两个以及两个以上的个数,再相乘。 } } return dp[n]; From 1b7c86e20c2b36ed0732deb66a0c124a8e8fcdff Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Mon, 7 Feb 2022 23:01:47 +0800 Subject: [PATCH 04/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880257.=E4=BA=8C?= =?UTF-8?q?=E5=8F=89=E6=A0=91=E7=9A=84=E6=89=80=E6=9C=89=E8=B7=AF=E5=BE=84?= =?UTF-8?q?.md=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0typescript=E7=89=88?= =?UTF-8?q?=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0257.二叉树的所有路径.md | 67 +++++++++++++++++++++-- 1 file changed, 61 insertions(+), 6 deletions(-) diff --git a/problems/0257.二叉树的所有路径.md b/problems/0257.二叉树的所有路径.md index 4078320f..1362897c 100644 --- a/problems/0257.二叉树的所有路径.md +++ b/problems/0257.二叉树的所有路径.md @@ -433,9 +433,9 @@ class Solution: if cur.right: self.traversal(cur.right, path + '->', result) ``` - + 迭代法: - + ```python3 from collections import deque @@ -463,13 +463,13 @@ class Solution: return result ``` - + --- Go: - + 递归法: - + ```go func binaryTreePaths(root *TreeNode) []string { res := make([]string, 0) @@ -492,7 +492,7 @@ func binaryTreePaths(root *TreeNode) []string { return res } ``` - + 迭代法: ```go @@ -581,7 +581,62 @@ var binaryTreePaths = function(root) { }; ``` +TypeScript: + +> 递归法 + +```typescript +function binaryTreePaths(root: TreeNode | null): string[] { + function recur(node: TreeNode, route: string, resArr: string[]): void { + route += String(node.val); + if (node.left === null && node.right === null) { + resArr.push(route); + return; + } + if (node.left !== null) recur(node.left, route + '->', resArr); + if (node.right !== null) recur(node.right, route + '->', resArr); + } + const resArr: string[] = []; + if (root === null) return resArr; + recur(root, '', resArr); + return resArr; +}; +``` + +> 迭代法 + +```typescript +// 迭代法2 +function binaryTreePaths(root: TreeNode | null): string[] { + let helperStack: TreeNode[] = []; + let tempNode: TreeNode; + let routeArr: string[] = []; + let resArr: string[] = []; + if (root !== null) { + helperStack.push(root); + routeArr.push(String(root.val)); + }; + while (helperStack.length > 0) { + tempNode = helperStack.pop()!; + let route: string = routeArr.pop()!; // tempNode 对应的路径 + if (tempNode.left === null && tempNode.right === null) { + resArr.push(route); + } + if (tempNode.right !== null) { + helperStack.push(tempNode.right); + routeArr.push(route + '->' + tempNode.right.val); // tempNode.right 对应的路径 + } + if (tempNode.left !== null) { + helperStack.push(tempNode.left); + routeArr.push(route + '->' + tempNode.left.val); // tempNode.left 对应的路径 + } + } + return resArr; +}; +``` + Swift: + > 递归/回溯 ```swift func binaryTreePaths(_ root: TreeNode?) -> [String] { From 47818c947888ecff3dae6f36daded1cfaf92db3b Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Tue, 8 Feb 2022 10:23:59 +0800 Subject: [PATCH 05/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=88=E4=BA=8C?= =?UTF-8?q?=E5=8F=89=E6=A0=91=E4=B8=AD=E9=80=92=E5=BD=92=E5=B8=A6=E7=9D=80?= =?UTF-8?q?=E5=9B=9E=E6=BA=AF.md=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E7=9B=B8=E5=90=8C=E7=9A=84=E6=A0=91typescript=E7=89=88?= =?UTF-8?q?=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/二叉树中递归带着回溯.md | 23 ++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/problems/二叉树中递归带着回溯.md b/problems/二叉树中递归带着回溯.md index 20b87f87..03815ed3 100644 --- a/problems/二叉树中递归带着回溯.md +++ b/problems/二叉树中递归带着回溯.md @@ -515,6 +515,29 @@ var binaryTreePaths = function(root) { }; ``` +TypeScript: + +> 相同的树 + +```typescript +function isSameTree(p: TreeNode | null, q: TreeNode | null): boolean { + if (p === null && q === null) return true; + if (p === null || q === null) return false; + if (p.val !== q.val) return false; + let bool1: boolean, bool2: boolean; + bool1 = isSameTree(p.left, q.left); + bool2 = isSameTree(p.right, q.right); + return bool1 && bool2; +}; +``` + +> 二叉树的不同路径 + +```typescript +``` + + + -----------------------
From 49a1a42bbed494b10b4d6659ba787830f62bd842 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Tue, 8 Feb 2022 10:45:15 +0800 Subject: [PATCH 06/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=88=E4=BA=8C?= =?UTF-8?q?=E5=8F=89=E6=A0=91=E4=B8=AD=E9=80=92=E5=BD=92=E5=B8=A6=E7=9D=80?= =?UTF-8?q?=E5=9B=9E=E6=BA=AF.md=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E4=BA=8C=E5=8F=89=E6=A0=91=E7=9A=84=E4=B8=8D=E5=90=8C=E8=B7=AF?= =?UTF-8?q?=E5=BE=84=E7=9A=84typescript=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/二叉树中递归带着回溯.md | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/problems/二叉树中递归带着回溯.md b/problems/二叉树中递归带着回溯.md index 03815ed3..41d5663e 100644 --- a/problems/二叉树中递归带着回溯.md +++ b/problems/二叉树中递归带着回溯.md @@ -534,6 +534,27 @@ function isSameTree(p: TreeNode | null, q: TreeNode | null): boolean { > 二叉树的不同路径 ```typescript +function binaryTreePaths(root: TreeNode | null): string[] { + function recur(node: TreeNode, nodeSeqArr: number[], resArr: string[]): void { + nodeSeqArr.push(node.val); + if (node.left === null && node.right === null) { + resArr.push(nodeSeqArr.join('->')); + } + if (node.left !== null) { + recur(node.left, nodeSeqArr, resArr); + nodeSeqArr.pop(); + } + if (node.right !== null) { + recur(node.right, nodeSeqArr, resArr); + nodeSeqArr.pop(); + } + } + let nodeSeqArr: number[] = []; + let resArr: string[] = []; + if (root === null) return resArr; + recur(root, nodeSeqArr, resArr); + return resArr; +}; ``` From f604aea34c6632e20ad4ced37cb24c005420e574 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Tue, 8 Feb 2022 23:00:31 +0800 Subject: [PATCH 07/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880404.=E5=B7=A6?= =?UTF-8?q?=E5=8F=B6=E5=AD=90=E4=B9=8B=E5=92=8C.md=EF=BC=89=EF=BC=9A?= =?UTF-8?q?=E5=A2=9E=E5=8A=A0typescript=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0404.左叶子之和.md | 44 ++++++++++++++++++++++++++++++++ 1 file changed, 44 insertions(+) diff --git a/problems/0404.左叶子之和.md b/problems/0404.左叶子之和.md index 09272052..2b4df151 100644 --- a/problems/0404.左叶子之和.md +++ b/problems/0404.左叶子之和.md @@ -372,6 +372,50 @@ var sumOfLeftLeaves = function(root) { }; ``` +## TypeScript + +> 递归法 + +```typescript +function sumOfLeftLeaves(root: TreeNode | null): number { + if (root === null) return 0; + let midVal: number = 0; + if ( + root.left !== null && + root.left.left === null && + root.left.right === null + ) { + midVal = root.left.val; + } + let leftVal: number = sumOfLeftLeaves(root.left); + let rightVal: number = sumOfLeftLeaves(root.right); + return midVal + leftVal + rightVal; +}; +``` + +> 迭代法 + +```typescript +function sumOfLeftLeaves(root: TreeNode | null): number { + let helperStack: TreeNode[] = []; + let tempNode: TreeNode; + let sum: number = 0; + if (root !== null) helperStack.push(root); + while (helperStack.length > 0) { + tempNode = helperStack.pop()!; + if ( + tempNode.left !== null && + tempNode.left.left === null && + tempNode.left.right === null + ) { + sum += tempNode.left.val; + } + if (tempNode.right !== null) helperStack.push(tempNode.right); + if (tempNode.left !== null) helperStack.push(tempNode.left); + } + return sum; +}; +``` ## Swift From 4ed65b50d174a3d9f89d0352ee30da95fcecece9 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Wed, 9 Feb 2022 22:45:31 +0800 Subject: [PATCH 08/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880513.=E6=89=BE?= =?UTF-8?q?=E6=A0=91=E5=B7=A6=E4=B8=8B=E8=A7=92=E7=9A=84=E5=80=BC.md?= =?UTF-8?q?=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0typescript=E7=89=88?= =?UTF-8?q?=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0513.找树左下角的值.md | 45 ++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) diff --git a/problems/0513.找树左下角的值.md b/problems/0513.找树左下角的值.md index 84ed3932..12c62c70 100644 --- a/problems/0513.找树左下角的值.md +++ b/problems/0513.找树左下角的值.md @@ -433,6 +433,51 @@ var findBottomLeftValue = function(root) { }; ``` +## TypeScript + +> 递归法: + +```typescript +function findBottomLeftValue(root: TreeNode | null): number { + function recur(root: TreeNode, depth: number): void { + if (root.left === null && root.right === null) { + if (depth > maxDepth) { + maxDepth = depth; + resVal = root.val; + } + return; + } + if (root.left !== null) recur(root.left, depth + 1); + if (root.right !== null) recur(root.right, depth + 1); + } + let maxDepth: number = 0; + let resVal: number = 0; + if (root === null) return resVal; + recur(root, 1); + return resVal; +}; +``` + +> 迭代法: + +```typescript +function findBottomLeftValue(root: TreeNode | null): number { + let helperQueue: TreeNode[] = []; + if (root !== null) helperQueue.push(root); + let resVal: number = 0; + let tempNode: TreeNode; + while (helperQueue.length > 0) { + resVal = helperQueue[0].val; + for (let i = 0, length = helperQueue.length; i < length; i++) { + tempNode = helperQueue.shift()!; + if (tempNode.left !== null) helperQueue.push(tempNode.left); + if (tempNode.right !== null) helperQueue.push(tempNode.right); + } + } + return resVal; +}; +``` + ## Swift 递归版本: From 7d8e9e8fae9d580013b717ff882bd9a942fe0e4f Mon Sep 17 00:00:00 2001 From: Guang-Hou <87743934+Guang-Hou@users.noreply.github.com> Date: Wed, 9 Feb 2022 16:37:44 -0500 Subject: [PATCH 09/44] =?UTF-8?q?Update=200701.=E4=BA=8C=E5=8F=89=E6=90=9C?= =?UTF-8?q?=E7=B4=A2=E6=A0=91=E4=B8=AD=E7=9A=84=E6=8F=92=E5=85=A5=E6=93=8D?= =?UTF-8?q?=E4=BD=9C.md?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Python 递归法- 无返回值的一种更简单的实现。 --- .../0701.二叉搜索树中的插入操作.md | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/problems/0701.二叉搜索树中的插入操作.md b/problems/0701.二叉搜索树中的插入操作.md index 468f2675..5e9fbdfe 100644 --- a/problems/0701.二叉搜索树中的插入操作.md +++ b/problems/0701.二叉搜索树中的插入操作.md @@ -310,6 +310,26 @@ class Solution: return root ``` +**递归法** - 无返回值 - another easier way +```python +class Solution: + def insertIntoBST(self, root: Optional[TreeNode], val: int) -> Optional[TreeNode]: + newNode = TreeNode(val) + if not root: return newNode + + if not root.left and val < root.val: + root.left = newNode + if not root.right and val > root.val: + root.right = newNode + + if val < root.val: + self.insertIntoBST(root.left, val) + if val > root.val: + self.insertIntoBST(root.right, val) + + return root +``` + **迭代法** 与无返回值的递归函数的思路大体一致 ```python From fc1a7e3e079958e6919bbc4fbe069a8d92e66322 Mon Sep 17 00:00:00 2001 From: zhaoninge Date: Thu, 10 Feb 2022 17:01:31 +0800 Subject: [PATCH 10/44] =?UTF-8?q?Update=200027.=E7=A7=BB=E9=99=A4=E5=85=83?= =?UTF-8?q?=E7=B4=A0.md?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 添加27. 移除元素 C++版相向双指针方法,该方法基于元素顺序可以改变的题目描述,使用双指针法改变了元素相对位置,确保了移动最少元素 --- problems/0027.移除元素.md | 31 +++++++++++++++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/problems/0027.移除元素.md b/problems/0027.移除元素.md index d69f2bcf..0c6f5129 100644 --- a/problems/0027.移除元素.md +++ b/problems/0027.移除元素.md @@ -106,6 +106,37 @@ public: 旧文链接:[数组:就移除个元素很难么?](https://programmercarl.com/0027.移除元素.html) +```CPP +/** +* 相向双指针方法,基于元素顺序可以改变的题目描述改变了元素相对位置,确保了移动最少元素 +* 时间复杂度:$O(n)$ +* 空间复杂度:$O(1)$ +*/ +class Solution { +public: + int removeElement(vector& nums, int val) { + int leftIndex = 0; + int rightIndex = nums.size() - 1; + while (leftIndex <= rightIndex) { + // 找左边等于val的元素 + while (leftIndex <= rightIndex && nums[leftIndex] != val){ + ++leftIndex; + } + // 找右边不等于val的元素 + while (leftIndex <= rightIndex && nums[rightIndex] == val) { + -- rightIndex; + } + // 将右边不等于val的元素覆盖左边等于val的元素 + if (leftIndex < rightIndex) { + nums[leftIndex++] = nums[rightIndex--]; + } + } + return leftIndex; // leftIndex一定指向了最终数组末尾的下一个元素 + } +}; +``` + + ## 相关题目推荐 * 26.删除排序数组中的重复项 From 71dd3eab9e9a005eec5669bfc25ba3cd4d27fb2f Mon Sep 17 00:00:00 2001 From: Luo <82520819+Jerry-306@users.noreply.github.com> Date: Fri, 11 Feb 2022 11:26:14 +0800 Subject: [PATCH 11/44] =?UTF-8?q?0059=20=20=E8=9E=BA=E6=97=8B=E7=9F=A9?= =?UTF-8?q?=E9=98=B5II=20=20=E9=A2=98=E7=9B=AE=E9=94=99=E8=AF=AF=E7=BA=A0?= =?UTF-8?q?=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0059.螺旋矩阵II.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/problems/0059.螺旋矩阵II.md b/problems/0059.螺旋矩阵II.md index 3f7a59ca..ff654358 100644 --- a/problems/0059.螺旋矩阵II.md +++ b/problems/0059.螺旋矩阵II.md @@ -10,7 +10,7 @@ [力扣题目链接](https://leetcode-cn.com/problems/spiral-matrix-ii/) -给定一个正整数 n,生成一个包含 1 到 $n^2$ 所有元素,且元素按顺时针顺序螺旋排列的正方形矩阵。 +给定一个正整数 n,生成一个包含 1 到 n^2 所有元素,且元素按顺时针顺序螺旋排列的正方形矩阵。 示例: From 305ef69d5878ecaf1b9655e7899d663290f53af5 Mon Sep 17 00:00:00 2001 From: weiting-cn <2254912@qq.com> Date: Fri, 11 Feb 2022 16:09:17 +0800 Subject: [PATCH 12/44] =?UTF-8?q?=E6=9B=B4=E6=96=B0=EF=BC=9A0015.=E4=B8=89?= =?UTF-8?q?=E6=95=B0=E4=B9=8B=E5=92=8C=EF=BC=8C0018.=E5=9B=9B=E6=95=B0?= =?UTF-8?q?=E4=B9=8B=E5=92=8C=EF=BC=88=E5=8E=BB=E9=87=8D=E4=BC=98=E5=8C=96?= =?UTF-8?q?=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0015.三数之和.md | 4 ++++ problems/0018.四数之和.md | 4 ++++ 2 files changed, 8 insertions(+) diff --git a/problems/0015.三数之和.md b/problems/0015.三数之和.md index e191eabc..9b59e66d 100644 --- a/problems/0015.三数之和.md +++ b/problems/0015.三数之和.md @@ -138,8 +138,12 @@ public: */ if (nums[i] + nums[left] + nums[right] > 0) { right--; + // 当前元素不合适了,可以去重 + while (left < right && nums[right] == nums[right + 1]) right--; } else if (nums[i] + nums[left] + nums[right] < 0) { left++; + // 不合适,去重 + while (left < right && nums[left] == nums[left - 1]) left++; } else { result.push_back(vector{nums[i], nums[left], nums[right]}); // 去重逻辑应该放在找到一个三元组之后 diff --git a/problems/0018.四数之和.md b/problems/0018.四数之和.md index bad258c1..c6c55d50 100644 --- a/problems/0018.四数之和.md +++ b/problems/0018.四数之和.md @@ -91,9 +91,13 @@ public: // nums[k] + nums[i] + nums[left] + nums[right] > target 会溢出 if (nums[k] + nums[i] > target - (nums[left] + nums[right])) { right--; + // 当前元素不合适了,可以去重 + while (left < right && nums[right] == nums[right + 1]) right--; // nums[k] + nums[i] + nums[left] + nums[right] < target 会溢出 } else if (nums[k] + nums[i] < target - (nums[left] + nums[right])) { left++; + // 不合适,去重 + while (left < right && nums[left] == nums[left - 1]) left++; } else { result.push_back(vector{nums[k], nums[i], nums[left], nums[right]}); // 去重逻辑应该放在找到一个四元组之后 From fbf52ee2bf0cad8c4231311ef2d87fc383a49a3c Mon Sep 17 00:00:00 2001 From: Luo <82520819+Jerry-306@users.noreply.github.com> Date: Fri, 11 Feb 2022 16:57:22 +0800 Subject: [PATCH 13/44] =?UTF-8?q?=E7=AE=97=E6=B3=95=E6=A8=A1=E6=9D=BF?= =?UTF-8?q?=E6=96=B0=E5=A2=9E=20typescript=20=E7=89=88=E6=9C=AC=E4=BB=A3?= =?UTF-8?q?=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/算法模板.md | 265 ++++++++++++++++++++++++++++++++++++++- 1 file changed, 264 insertions(+), 1 deletion(-) diff --git a/problems/算法模板.md b/problems/算法模板.md index a4136511..789d8f80 100644 --- a/problems/算法模板.md +++ b/problems/算法模板.md @@ -394,7 +394,7 @@ var postorder = function (root, list) { ```javascript var preorderTraversal = function (root) { let res = []; - if (root === null) return rs; + if (root === null) return res; let stack = [root], cur = null; while (stack.length) { @@ -536,6 +536,269 @@ function backtracking(参数) { } ``` +TypeScript: + +## 二分查找法 + +使用左闭右闭区间 + +```typescript +var search = function (nums: number[], target: number): number { + let left: number = 0, right: number = nums.length - 1; + // 使用左闭右闭区间 + while (left <= right) { + let mid: number = left + Math.floor((right - left)/2); + if (nums[mid] > target) { + right = mid - 1; // 去左面闭区间寻找 + } else if (nums[mid] < target) { + left = mid + 1; // 去右面闭区间寻找 + } else { + return mid; + } + } + return -1; +}; +``` + +使用左闭右开区间 + +```typescript +var search = function (nums: number[], target: number): number { + let left: number = 0, right: number = nums.length; + // 使用左闭右开区间 [left, right) + while (left < right) { + let mid: number = left + Math.floor((right - left)/2); + if (nums[mid] > target) { + right = mid; // 去左面闭区间寻找 + } else if (nums[mid] < target) { + left = mid + 1; // 去右面闭区间寻找 + } else { + return mid; + } + } + return -1; +}; +``` + +## KMP + +```typescript +var kmp = function (next: number[], s: number): void { + next[0] = -1; + let j: number = -1; + for(let i: number = 1; i < s.length; i++){ + while (j >= 0 && s[i] !== s[j + 1]) { + j = next[j]; + } + if (s[i] === s[j + 1]) { + j++; + } + next[i] = j; + } +} +``` + +## 二叉树 + +### 深度优先遍历(递归) + +二叉树节点定义: + +```typescript +class TreeNode { + val: number + left: TreeNode | null + right: TreeNode | null + constructor(val?: number, left?: TreeNode | null, right?: TreeNode | null) { + this.val = (val===undefined ? 0 : val) + this.left = (left===undefined ? null : left) + this.right = (right===undefined ? null : right) + } +} +``` + +前序遍历(中左右): + +```typescript +var preorder = function (root: TreeNode | null, list: number[]): void { + if (root === null) return; + list.push(root.val); // 中 + preorder(root.left, list); // 左 + preorder(root.right, list); // 右 +} +``` + +中序遍历(左中右): + +```typescript +var inorder = function (root: TreeNode | null, list: number[]): void { + if (root === null) return; + inorder(root.left, list); // 左 + list.push(root.val); // 中 + inorder(root.right, list); // 右 +} +``` + +后序遍历(左右中): + +```typescript +var postorder = function (root: TreeNode | null, list: number[]): void { + if (root === null) return; + postorder(root.left, list); // 左 + postorder(root.right, list); // 右 + list.push(root.val); // 中 +} +``` + +### 深度优先遍历(迭代) + +前序遍历(中左右): + +```typescript +var preorderTraversal = function (root: TreeNode | null): number[] { + let res: number[] = []; + if (root === null) return res; + let stack: TreeNode[] = [root], + cur: TreeNode | null = null; + while (stack.length) { + cur = stack.pop(); + res.push(cur.val); + cur.right && stack.push(cur.right); + cur.left && stack.push(cur.left); + } + return res; +}; +``` + +中序遍历(左中右): + +```typescript +var inorderTraversal = function (root: TreeNode | null): number[] { + let res: number[] = []; + if (root === null) return res; + let stack: TreeNode[] = []; + let cur: TreeNode | null = root; + while (stack.length !== 0 || cur !== null) { + if (cur !== null) { + stack.push(cur); + cur = cur.left; + } else { + cur = stack.pop(); + res.push(cur.val); + cur = cur.right; + } + } + return res; +}; +``` + +后序遍历(左右中): + +```typescript +var postorderTraversal = function (root: TreeNode | null): number[] { + let res: number[] = []; + if (root === null) return res; + let stack: TreeNode[] = [root]; + let cur: TreeNode | null = null; + while (stack.length) { + cur = stack.pop(); + res.push(cur.val); + cur.left && stack.push(cur.left); + cur.right && stack.push(cur.right); + } + return res.reverse() +}; +``` + +### 广度优先遍历(队列) + +```typescript +var levelOrder = function (root: TreeNode | null): number[] { + let res: number[] = []; + if (root === null) return res; + let queue: TreeNode[] = [root]; + while (queue.length) { + let n: number = queue.length; + let temp: number[] = []; + for (let i: number = 0; i < n; i++) { + let node: TreeNode = queue.shift(); + temp.push(node.val); + node.left && queue.push(node.left); + node.right && queue.push(node.right); + } + res.push(temp); + } + return res; +}; +``` + +### 二叉树深度 + +```typescript +var getDepth = function (node: TreNode | null): number { + if (node === null) return 0; + return 1 + Math.max(getDepth(node.left), getDepth(node.right)); +} +``` + +### 二叉树节点数量 + +```typescript +var countNodes = function (root: TreeNode | null): number { + if (root === null) return 0; + return 1 + countNodes(root.left) + countNodes(root.right); +} +``` + +## 回溯算法 + +```typescript +function backtracking(参数) { + if (终止条件) { + 存放结果; + return; + } + + for (选择:本层集合中元素(树中节点孩子的数量就是集合的大小)) { + 处理节点; + backtracking(路径,选择列表); // 递归 + 回溯,撤销处理结果 + } +} + +``` + +## 并查集 + +```typescript + let n: number = 1005; // 根据题意而定 + let father: number[] = new Array(n).fill(0); + + // 并查集初始化 + function init () { + for (int i: number = 0; i < n; ++i) { + father[i] = i; + } + } + // 并查集里寻根的过程 + function find (u: number): number { + return u === father[u] ? u : father[u] = find(father[u]); + } + // 将v->u 这条边加入并查集 + function join(u: number, v: number) { + u = find(u); + v = find(v); + if (u === v) return ; + father[v] = u; + } + // 判断 u 和 v是否找到同一个根 + function same(u: number, v: number): boolean { + u = find(u); + v = find(v); + return u === v; + } +``` + Java: From 65a341bf365eb3b2648c357a7a311a59ec6e9e18 Mon Sep 17 00:00:00 2001 From: Larry Liu Date: Fri, 11 Feb 2022 20:24:45 +0800 Subject: [PATCH 14/44] =?UTF-8?q?Update=20=E5=B9=BF=E5=B7=9E=E4=BA=92?= =?UTF-8?q?=E8=81=94=E7=BD=91=E5=85=AC=E5=8F=B8=E6=80=BB=E7=BB=93.md?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 字节跳动有广州研发岗位 --- problems/前序/广州互联网公司总结.md | 1 + 1 file changed, 1 insertion(+) diff --git a/problems/前序/广州互联网公司总结.md b/problems/前序/广州互联网公司总结.md index ae41c899..ac70f40c 100644 --- a/problems/前序/广州互联网公司总结.md +++ b/problems/前序/广州互联网公司总结.md @@ -14,6 +14,7 @@ ## 一线互联网 * 微信(总部) 有点难进! +* 字节跳动(广州) ## 二线 * 网易(总部)主要是游戏 From 961ae6eadf6359f2ef6b787ad612475e02e6842e Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Fri, 11 Feb 2022 21:52:36 +0800 Subject: [PATCH 15/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880112.=E8=B7=AF?= =?UTF-8?q?=E5=BE=84=E6=80=BB=E5=92=8C.md=EF=BC=89=EF=BC=9A=E5=A2=9E?= =?UTF-8?q?=E5=8A=A0typescript=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0112.路径总和.md | 89 +++++++++++++++++++++++++++++++++++ 1 file changed, 89 insertions(+) diff --git a/problems/0112.路径总和.md b/problems/0112.路径总和.md index 5ec8ffd0..de6caef0 100644 --- a/problems/0112.路径总和.md +++ b/problems/0112.路径总和.md @@ -766,11 +766,100 @@ let pathSum = function(root, targetSum) { }; ``` +## TypeScript + +> 0112.路径总和 + +**递归法:** + +```typescript +function hasPathSum(root: TreeNode | null, targetSum: number): boolean { + function recur(node: TreeNode, sum: number): boolean { + console.log(sum); + if ( + node.left === null && + node.right === null && + sum === 0 + ) return true; + if (node.left !== null) { + sum -= node.left.val; + if (recur(node.left, sum) === true) return true; + sum += node.left.val; + } + if (node.right !== null) { + sum -= node.right.val; + if (recur(node.right, sum) === true) return true; + sum += node.right.val; + } + return false; + } + if (root === null) return false; + return recur(root, targetSum - root.val); +}; +``` + +**递归法(精简版):** + +```typescript +function hasPathSum(root: TreeNode | null, targetSum: number): boolean { + if (root === null) return false; + targetSum -= root.val; + if ( + root.left === null && + root.right === null && + targetSum === 0 + ) return true; + return hasPathSum(root.left, targetSum) || + hasPathSum(root.right, targetSum); +}; +``` + +**迭代法:** + +```typescript +function hasPathSum(root: TreeNode | null, targetSum: number): boolean { + type Pair = { + node: TreeNode, // 当前节点 + sum: number // 根节点到当前节点的路径数值总和 + } + + const helperStack: Pair[] = []; + if (root !== null) helperStack.push({ node: root, sum: root.val }); + let tempPair: Pair; + while (helperStack.length > 0) { + tempPair = helperStack.pop()!; + if ( + tempPair.node.left === null && + tempPair.node.right === null && + tempPair.sum === targetSum + ) return true; + if (tempPair.node.right !== null) { + helperStack.push({ + node: tempPair.node.right, + sum: tempPair.sum + tempPair.node.right.val + }); + } + if (tempPair.node.left !== null) { + helperStack.push({ + node: tempPair.node.left, + sum: tempPair.sum + tempPair.node.left.val + }); + } + } + return false; +}; +``` + +> 0112.路径总和 ii + + + ## Swift 0112.路径总和 **递归** + ```swift func hasPathSum(_ root: TreeNode?, _ targetSum: Int) -> Bool { guard let root = root else { From fde074cb2ab400b44707c178139d7757541bbf39 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Fri, 11 Feb 2022 23:28:30 +0800 Subject: [PATCH 16/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880112.=E8=B7=AF?= =?UTF-8?q?=E5=BE=84=E6=80=BB=E5=92=8C=20ii=EF=BC=89=EF=BC=9A=E5=A2=9E?= =?UTF-8?q?=E5=8A=A0typescript=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0112.路径总和.md | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/problems/0112.路径总和.md b/problems/0112.路径总和.md index de6caef0..2e10d98d 100644 --- a/problems/0112.路径总和.md +++ b/problems/0112.路径总和.md @@ -852,7 +852,39 @@ function hasPathSum(root: TreeNode | null, targetSum: number): boolean { > 0112.路径总和 ii +**递归法:** +```typescript +function pathSum(root: TreeNode | null, targetSum: number): number[][] { + function recur(node: TreeNode, sumGap: number, routeArr: number[]): void { + if ( + node.left === null && + node.right === null && + sumGap === 0 + ) resArr.push([...routeArr]); + if (node.left !== null) { + sumGap -= node.left.val; + routeArr.push(node.left.val); + recur(node.left, sumGap, routeArr); + sumGap += node.left.val; + routeArr.pop(); + } + if (node.right !== null) { + sumGap -= node.right.val; + routeArr.push(node.right.val); + recur(node.right, sumGap, routeArr); + sumGap += node.right.val; + routeArr.pop(); + } + } + const resArr: number[][] = []; + if (root === null) return resArr; + const routeArr: number[] = []; + routeArr.push(root.val); + recur(root, targetSum - root.val, routeArr); + return resArr; +}; +``` ## Swift From fb67fb4320c3ee7c0ee17dd695a5b7a7ea2a4d34 Mon Sep 17 00:00:00 2001 From: "darion.yaphet" Date: Sat, 12 Feb 2022 17:25:57 +0800 Subject: [PATCH 17/44] fix java code --- problems/背包理论基础01背包-1.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/problems/背包理论基础01背包-1.md b/problems/背包理论基础01背包-1.md index 6ff32017..fe940b4c 100644 --- a/problems/背包理论基础01背包-1.md +++ b/problems/背包理论基础01背包-1.md @@ -271,7 +271,7 @@ int main() { ### java ```java - public static void main(string[] args) { + public static void main(String[] args) { int[] weight = {1, 3, 4}; int[] value = {15, 20, 30}; int bagsize = 4; @@ -292,16 +292,16 @@ int main() { if (j < weight[i - 1]){ dp[i][j] = dp[i - 1][j]; }else{ - dp[i][j] = math.max(dp[i - 1][j], dp[i - 1][j - weight[i - 1]] + value[i - 1]); + dp[i][j] = Math.max(dp[i - 1][j], dp[i - 1][j - weight[i - 1]] + value[i - 1]); } } } //打印dp数组 for (int i = 0; i <= wlen; i++){ for (int j = 0; j <= bagsize; j++){ - system.out.print(dp[i][j] + " "); + System.out.print(dp[i][j] + " "); } - system.out.print("\n"); + System.out.print("\n"); } } ``` From bac5f8d70cef72f5457ac80fd487d86618d27831 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Sun, 13 Feb 2022 16:37:32 +0800 Subject: [PATCH 18/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880106.=E4=BB=8E?= =?UTF-8?q?=E4=B8=AD=E5=BA=8F=E4=B8=8E=E5=90=8E=E5=BA=8F=E9=81=8D=E5=8E=86?= =?UTF-8?q?=E5=BA=8F=E5=88=97=E6=9E=84=E9=80=A0=E4=BA=8C=E5=8F=89=E6=A0=91?= =?UTF-8?q?.md=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0typescript=E7=89=88?= =?UTF-8?q?=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...序与后序遍历序列构造二叉树.md | 63 +++++++++++++++++++ 1 file changed, 63 insertions(+) diff --git a/problems/0106.从中序与后序遍历序列构造二叉树.md b/problems/0106.从中序与后序遍历序列构造二叉树.md index 40d75983..9b18e729 100644 --- a/problems/0106.从中序与后序遍历序列构造二叉树.md +++ b/problems/0106.从中序与后序遍历序列构造二叉树.md @@ -814,7 +814,70 @@ var buildTree = function(preorder, inorder) { }; ``` +## TypeScript + +> 106.从中序与后序遍历序列构造二叉树 + +**创建新数组:** + +```typescript +function buildTree(inorder: number[], postorder: number[]): TreeNode | null { + if (postorder.length === 0) return null; + const rootVal: number = postorder.pop()!; + const rootValIndex: number = inorder.indexOf(rootVal); + const rootNode: TreeNode = new TreeNode(rootVal); + rootNode.left = buildTree(inorder.slice(0, rootValIndex), postorder.slice(0, rootValIndex)); + rootNode.right = buildTree(inorder.slice(rootValIndex + 1), postorder.slice(rootValIndex)); + return rootNode; +}; +``` + +**使用数组索引:** + +```typescript +function buildTree(inorder: number[], postorder: number[]): TreeNode | null { + function recur( + inorder: number[], postorder: number[], + inBegin: number, inEnd: number, + postBegin: number, postEnd: number + ): TreeNode | null { + if (postBegin === postEnd) return null; + const rootVal: number = postorder[postEnd - 1]!; + const rootValIndex: number = inorder.indexOf(rootVal, inBegin); + const rootNode: TreeNode = new TreeNode(rootVal); + + const leftInorderBegin: number = inBegin; + const leftInorderEnd: number = rootValIndex; + const rightInorderBegin: number = rootValIndex + 1; + const rightInorderEnd: number = inEnd; + + const leftPostorderBegin: number = postBegin; + const leftPostorderEnd: number = postBegin + rootValIndex - inBegin; + const rightPostorderBegin: number = leftPostorderEnd; + const rightPostorderEnd: number = postEnd - 1; + + rootNode.left = recur( + inorder, postorder, + leftInorderBegin, leftInorderEnd, + leftPostorderBegin, leftPostorderEnd + ); + rootNode.right = recur( + inorder, postorder, + rightInorderBegin, rightInorderEnd, + rightPostorderBegin, rightPostorderEnd + ); + return rootNode; + } + return recur(inorder, postorder, 0, inorder.length, 0, inorder.length); +}; +``` + +> 105.从前序与中序遍历序列构造二叉树 + + + ## C + 106 从中序与后序遍历序列构造二叉树 ```c From ddf79ac04322e27c50f50be81a46407d7b054950 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Sun, 13 Feb 2022 17:09:38 +0800 Subject: [PATCH 19/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=88105.=E4=BB=8E?= =?UTF-8?q?=E5=89=8D=E5=BA=8F=E4=B8=8E=E4=B8=AD=E5=BA=8F=E9=81=8D=E5=8E=86?= =?UTF-8?q?=E5=BA=8F=E5=88=97=E6=9E=84=E9=80=A0=E4=BA=8C=E5=8F=89=E6=A0=91?= =?UTF-8?q?=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0typescript=E7=89=88?= =?UTF-8?q?=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...序与后序遍历序列构造二叉树.md | 44 +++++++++++++++++++ 1 file changed, 44 insertions(+) diff --git a/problems/0106.从中序与后序遍历序列构造二叉树.md b/problems/0106.从中序与后序遍历序列构造二叉树.md index 9b18e729..3e4211fb 100644 --- a/problems/0106.从中序与后序遍历序列构造二叉树.md +++ b/problems/0106.从中序与后序遍历序列构造二叉树.md @@ -874,7 +874,51 @@ function buildTree(inorder: number[], postorder: number[]): TreeNode | null { > 105.从前序与中序遍历序列构造二叉树 +**新建数组:** +```typescript +function buildTree(preorder: number[], inorder: number[]): TreeNode | null { + if (preorder.length === 0) return null; + const rootVal: number = preorder[0]; + const rootNode: TreeNode = new TreeNode(rootVal); + const rootValIndex: number = inorder.indexOf(rootVal); + rootNode.left = buildTree(preorder.slice(1, rootValIndex + 1), inorder.slice(0, rootValIndex)); + rootNode.right = buildTree(preorder.slice(rootValIndex + 1), inorder.slice(rootValIndex + 1)); + return rootNode; +}; +``` + +**使用数组索引:** + +```typescript +function buildTree(preorder: number[], inorder: number[]): TreeNode | null { + function recur( + preorder: number[], inorder: number[], + preBegin: number, preEnd: number, + inBegin: number, inEnd: number + ): TreeNode | null { + if (preBegin === preEnd) return null; + const rootVal: number = preorder[preBegin]; + const rootNode: TreeNode = new TreeNode(rootVal); + const rootValIndex: number = inorder.indexOf(rootVal, inBegin); + + const leftPreBegin: number = preBegin + 1; + const leftPreEnd: number = preBegin + rootValIndex - inBegin + 1; + const leftInBegin: number = inBegin; + const leftInEnd: number = rootValIndex; + + const rightPreBegin: number = leftPreEnd; + const rightPreEnd: number = preEnd; + const rightInBegin: number = rootValIndex + 1; + const rightInEnd: number = inEnd; + + rootNode.left = recur(preorder, inorder, leftPreBegin, leftPreEnd, leftInBegin, leftInEnd); + rootNode.right = recur(preorder, inorder, rightPreBegin, rightPreEnd, rightInBegin, rightInEnd); + return rootNode; + }; + return recur(preorder, inorder, 0, preorder.length, 0, inorder.length); +}; +``` ## C From 92322870fe4664dffa3dcb8e6020626376417bb3 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Sun, 13 Feb 2022 21:20:24 +0800 Subject: [PATCH 20/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880654.=E6=9C=80?= =?UTF-8?q?=E5=A4=A7=E4=BA=8C=E5=8F=89=E6=A0=91.md=EF=BC=89=EF=BC=9A?= =?UTF-8?q?=E5=A2=9E=E5=8A=A0typescript=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0654.最大二叉树.md | 49 ++++++++++++++++++++++++++++++++ 1 file changed, 49 insertions(+) diff --git a/problems/0654.最大二叉树.md b/problems/0654.最大二叉树.md index 44c74f89..1c73354b 100644 --- a/problems/0654.最大二叉树.md +++ b/problems/0654.最大二叉树.md @@ -371,7 +371,56 @@ var constructMaximumBinaryTree = function (nums) { }; ``` +## TypeScript + +> 新建数组法: + +```typescript +function constructMaximumBinaryTree(nums: number[]): TreeNode | null { + if (nums.length === 0) return null; + let maxIndex: number = 0; + let maxVal: number = nums[0]; + for (let i = 1, length = nums.length; i < length; i++) { + if (nums[i] > maxVal) { + maxIndex = i; + maxVal = nums[i]; + } + } + const rootNode: TreeNode = new TreeNode(maxVal); + rootNode.left = constructMaximumBinaryTree(nums.slice(0, maxIndex)); + rootNode.right = constructMaximumBinaryTree(nums.slice(maxIndex + 1)); + return rootNode; +}; +``` + +> 使用数组索引法: + +```typescript +function constructMaximumBinaryTree(nums: number[]): TreeNode | null { + // 左闭右开区间[begin, end) + function recur(nums: number[], begin: number, end: number): TreeNode | null { + if (begin === end) return null; + let maxIndex: number = begin; + let maxVal: number = nums[begin]; + for (let i = begin + 1; i < end; i++) { + if (nums[i] > maxVal) { + maxIndex = i; + maxVal = nums[i]; + } + } + const rootNode: TreeNode = new TreeNode(maxVal); + rootNode.left = recur(nums, begin, maxIndex); + rootNode.right = recur(nums, maxIndex + 1, end); + return rootNode; + } + return recur(nums, 0, nums.length); +}; +``` + + + ## C + ```c struct TreeNode* traversal(int* nums, int left, int right) { //若左边界大于右边界,返回NULL From 2440d6a365def0caf92f041886545117ec0c1e9f Mon Sep 17 00:00:00 2001 From: Dewittt <43514251+Dewittt@users.noreply.github.com> Date: Mon, 14 Feb 2022 14:04:34 +0800 Subject: [PATCH 21/44] =?UTF-8?q?Update=20=E8=83=8C=E5=8C=85=E9=97=AE?= =?UTF-8?q?=E9=A2=98=E7=90=86=E8=AE=BA=E5=9F=BA=E7=A1=80=E5=AE=8C=E5=85=A8?= =?UTF-8?q?=E8=83=8C=E5=8C=85.md?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 删除多余字符 --- problems/背包问题理论基础完全背包.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/problems/背包问题理论基础完全背包.md b/problems/背包问题理论基础完全背包.md index cea69c72..2cdfeffa 100644 --- a/problems/背包问题理论基础完全背包.md +++ b/problems/背包问题理论基础完全背包.md @@ -94,7 +94,7 @@ dp状态图如下: 看了这两个图,大家就会理解,完全背包中,两个for循环的先后循序,都不影响计算dp[j]所需要的值(这个值就是下标j之前所对应的dp[j])。 -先遍历被背包在遍历物品,代码如下: +先遍历背包在遍历物品,代码如下: ```CPP // 先遍历背包,再遍历物品 From 30f2c6bc1763bb3cfe607707f96b1d9047a3d2b3 Mon Sep 17 00:00:00 2001 From: Verolilo <57696907+Verolilo@users.noreply.github.com> Date: Mon, 14 Feb 2022 14:15:33 +0800 Subject: [PATCH 22/44] =?UTF-8?q?=E6=9B=B4=E6=96=B00070.=E7=88=AC=E6=A5=BC?= =?UTF-8?q?=E6=A2=AF.md=20python=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 更新0070.爬楼梯.md python版本,添加了O(1)复杂度的python代码 --- problems/0070.爬楼梯.md | 28 ++++++++++++++++++++-------- 1 file changed, 20 insertions(+), 8 deletions(-) diff --git a/problems/0070.爬楼梯.md b/problems/0070.爬楼梯.md index 7f47a991..da19ea0e 100644 --- a/problems/0070.爬楼梯.md +++ b/problems/0070.爬楼梯.md @@ -256,16 +256,28 @@ public int climbStairs(int n) { ### Python ```python +# 空间复杂度为O(n)版本 class Solution: def climbStairs(self, n: int) -> int: - # dp[i]表示爬到第i级楼梯的种数, (1, 2) (2, 1)是两种不同的类型 - dp = [0] * (n + 1) - dp[0] = 1 - for i in range(n+1): - for j in range(1, 3): - if i>=j: - dp[i] += dp[i-j] - return dp[-1] + # dp[i] 为第 i 阶楼梯有多少种方法爬到楼顶 + dp=[0]*(n+1) + dp[0]=1 + dp[1]=1 + for i in range(2,n+1): + dp[i]=dp[i-1]+dp[i-2] + return dp[n] + +# 空间复杂度为O(1)版本 +class Solution: + def climbStairs(self, n: int) -> int: + dp=[0]*(n+1) + dp[0]=1 + dp[1]=1 + for i in range(2,n+1): + tmp=dp[0]+dp[1] + dp[0]=dp[1] + dp[1]=tmp + return dp[1] ``` ### Go From 6d5a0d0340798f773104f418d3db71797c5db717 Mon Sep 17 00:00:00 2001 From: Verolilo <57696907+Verolilo@users.noreply.github.com> Date: Wed, 16 Feb 2022 10:22:19 +0800 Subject: [PATCH 23/44] =?UTF-8?q?=E6=9B=B4=E6=96=B00213.=E6=89=93=E5=AE=B6?= =?UTF-8?q?=E5=8A=AB=E8=88=8DII.md=20=E6=9B=B4=E7=AE=80=E6=B4=81=E7=9A=84p?= =?UTF-8?q?ython=20=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0213.打家劫舍II.md | 32 +++++++++++++++++--------------- 1 file changed, 17 insertions(+), 15 deletions(-) diff --git a/problems/0213.打家劫舍II.md b/problems/0213.打家劫舍II.md index b6c2d080..8e569e46 100644 --- a/problems/0213.打家劫舍II.md +++ b/problems/0213.打家劫舍II.md @@ -123,22 +123,24 @@ 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) + #在198入门级的打家劫舍问题上分两种情况考虑 + #一是不偷第一间房,二是不偷最后一间房 + if len(nums)==1:#题目中提示nums.length>=1,所以不需要考虑len(nums)==0的情况 + return nums[0] + val1=self.roblist(nums[1:])#不偷第一间房 + val2=self.roblist(nums[:-1])#不偷最后一间房 + return max(val1,val2) - 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] + def robRange(self,nums): + l=len(nums) + dp=[0]*l + dp[0]=nums[0] + for i in range(1,l): + if i==1: + dp[i]=max(dp[i-1],nums[i]) + else: + dp[i]=max(dp[i-1],dp[i-2]+nums[i]) + return dp[-1] ``` javascipt: From f39d5a110c19963037374a3f1ea253b30f08becb Mon Sep 17 00:00:00 2001 From: erdengk <15596570256@163.com> Date: Wed, 16 Feb 2022 16:23:39 +0800 Subject: [PATCH 24/44] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E9=83=A8=E5=88=86?= =?UTF-8?q?=E9=94=99=E5=AD=97=20&=20=E4=BC=98=E5=8C=96=E5=8F=98=E9=87=8F?= =?UTF-8?q?=E5=90=8D=E5=91=BD=E5=90=8D?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...序与后序遍历序列构造二叉树.md | 4 ++-- problems/0860.柠檬水找零.md | 20 +++++++++---------- 2 files changed, 12 insertions(+), 12 deletions(-) diff --git a/problems/0106.从中序与后序遍历序列构造二叉树.md b/problems/0106.从中序与后序遍历序列构造二叉树.md index 30ec684d..cb1d75d9 100644 --- a/problems/0106.从中序与后序遍历序列构造二叉树.md +++ b/problems/0106.从中序与后序遍历序列构造二叉树.md @@ -89,9 +89,9 @@ TreeNode* traversal (vector& inorder, vector& postorder) { **难点大家应该发现了,就是如何切割,以及边界值找不好很容易乱套。** -此时应该注意确定切割的标准,是左闭右开,还有左开又闭,还是左闭又闭,这个就是不变量,要在递归中保持这个不变量。 +此时应该注意确定切割的标准,是左闭右开,还有左开右闭,还是左闭右闭,这个就是不变量,要在递归中保持这个不变量。 -**在切割的过程中会产生四个区间,把握不好不变量的话,一会左闭右开,一会左闭又闭,必然乱套!** +**在切割的过程中会产生四个区间,把握不好不变量的话,一会左闭右开,一会左闭右闭,必然乱套!** 我在[数组:每次遇到二分法,都是一看就会,一写就废](https://programmercarl.com/0035.搜索插入位置.html)和[数组:这个循环可以转懵很多人!](https://programmercarl.com/0059.螺旋矩阵II.html)中都强调过循环不变量的重要性,在二分查找以及螺旋矩阵的求解中,坚持循环不变量非常重要,本题也是。 diff --git a/problems/0860.柠檬水找零.md b/problems/0860.柠檬水找零.md index 01bd1a3b..f48ecf4d 100644 --- a/problems/0860.柠檬水找零.md +++ b/problems/0860.柠檬水找零.md @@ -128,24 +128,24 @@ public: ```java class Solution { public boolean lemonadeChange(int[] bills) { - int cash_5 = 0; - int cash_10 = 0; + int five = 0; + int ten = 0; for (int i = 0; i < bills.length; i++) { if (bills[i] == 5) { - cash_5++; + five++; } else if (bills[i] == 10) { - cash_5--; - cash_10++; + five--; + ten++; } else if (bills[i] == 20) { - if (cash_10 > 0) { - cash_10--; - cash_5--; + if (ten > 0) { + ten--; + five--; } else { - cash_5 -= 3; + five -= 3; } } - if (cash_5 < 0 || cash_10 < 0) return false; + if (five < 0 || ten < 0) return false; } return true; From 1a553b01d691478c049fd39e59548f3a71c9f456 Mon Sep 17 00:00:00 2001 From: erdengk <15596570256@163.com> Date: Wed, 16 Feb 2022 17:43:36 +0800 Subject: [PATCH 25/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=200491.=E9=80=92?= =?UTF-8?q?=E5=A2=9E=E5=AD=90=E5=BA=8F=E5=88=97.md=20Java=E8=A7=A3?= =?UTF-8?q?=E6=B3=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0491.递增子序列.md | 34 +++++++++++++++++++++++++++++++- 1 file changed, 33 insertions(+), 1 deletion(-) diff --git a/problems/0491.递增子序列.md b/problems/0491.递增子序列.md index 6d88119e..298586c7 100644 --- a/problems/0491.递增子序列.md +++ b/problems/0491.递增子序列.md @@ -227,7 +227,39 @@ class Solution { } } ``` - +```java +//法二:使用map +class Solution { + //结果集合 + List> res = new ArrayList<>(); + //路径集合 + LinkedList path = new LinkedList<>(); + public List> findSubsequences(int[] nums) { + getSubsequences(nums,0); + return res; + } + private void getSubsequences( int[] nums, int start ) { + if(path.size()>1 ){ + res.add( new ArrayList<>(path) ); + // 注意这里不要加return,要取树上的节点 + } + HashMap map = new HashMap<>(); + for(int i=start ;i < nums.length ;i++){ + if(!path.isEmpty() && nums[i]< path.getLast()){ + continue; + } + // 使用过了当前数字 + if ( map.getOrDefault( nums[i],0 ) >=1 ){ + continue; + } + map.put(nums[i],map.getOrDefault( nums[i],0 )+1); + path.add( nums[i] ); + getSubsequences( nums,i+1 ); + path.removeLast(); + } + } +} +``` ### Python From fac4fc5193caac05a5418338f281e25c02a2739b Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Wed, 16 Feb 2022 23:22:26 +0800 Subject: [PATCH 26/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880617.=E5=90=88?= =?UTF-8?q?=E5=B9=B6=E4=BA=8C=E5=8F=89=E6=A0=91.md=EF=BC=89=EF=BC=9A?= =?UTF-8?q?=E5=A2=9E=E5=8A=A0typescript=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0617.合并二叉树.md | 50 ++++++++++++++++++++++++++++++++ 1 file changed, 50 insertions(+) diff --git a/problems/0617.合并二叉树.md b/problems/0617.合并二叉树.md index f815d741..55786ea9 100644 --- a/problems/0617.合并二叉树.md +++ b/problems/0617.合并二叉树.md @@ -583,6 +583,56 @@ var mergeTrees = function(root1, root2) { ``` +## TypeScript + +> 递归法: + +```type +function mergeTrees(root1: TreeNode | null, root2: TreeNode | null): TreeNode | null { + if (root1 === null) return root2; + if (root2 === null) return root1; + const resNode: TreeNode = new TreeNode(root1.val + root2.val); + resNode.left = mergeTrees(root1.left, root2.left); + resNode.right = mergeTrees(root1.right, root2.right); + return resNode; +}; +``` + +> 迭代法: + +```typescript +function mergeTrees(root1: TreeNode | null, root2: TreeNode | null): TreeNode | null { + if (root1 === null) return root2; + if (root2 === null) return root1; + const helperQueue1: TreeNode[] = [], + helperQueue2: TreeNode[] = []; + helperQueue1.push(root1); + helperQueue2.push(root2); + let tempNode1: TreeNode, + tempNode2: TreeNode; + while (helperQueue1.length > 0) { + tempNode1 = helperQueue1.shift()!; + tempNode2 = helperQueue2.shift()!; + tempNode1.val += tempNode2.val; + if (tempNode1.left !== null && tempNode2.left !== null) { + helperQueue1.push(tempNode1.left); + helperQueue2.push(tempNode2.left); + } else if (tempNode1.left === null) { + tempNode1.left = tempNode2.left; + } + if (tempNode1.right !== null && tempNode2.right !== null) { + helperQueue1.push(tempNode1.right); + helperQueue2.push(tempNode2.right); + } else if (tempNode1.right === null) { + tempNode1.right = tempNode2.right; + } + } + return root1; +}; +``` + + + -----------------------
From bd2310622b8a4d726288759820a60b5a62fce590 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Thu, 17 Feb 2022 10:25:56 +0800 Subject: [PATCH 27/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880700.=E4=BA=8C?= =?UTF-8?q?=E5=8F=89=E6=90=9C=E7=B4=A2=E6=A0=91=E4=B8=AD=E7=9A=84=E6=90=9C?= =?UTF-8?q?=E7=B4=A2.md=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0typescript?= =?UTF-8?q?=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0700.二叉搜索树中的搜索.md | 30 ++++++++++++++++++++ 1 file changed, 30 insertions(+) diff --git a/problems/0700.二叉搜索树中的搜索.md b/problems/0700.二叉搜索树中的搜索.md index 1521514a..00ba8753 100644 --- a/problems/0700.二叉搜索树中的搜索.md +++ b/problems/0700.二叉搜索树中的搜索.md @@ -334,6 +334,36 @@ var searchBST = function (root, val) { }; ``` +## TypeScript + +> 递归法 + +```typescript +function searchBST(root: TreeNode | null, val: number): TreeNode | null { + if (root === null || root.val === val) return root; + if (root.val < val) return searchBST(root.right, val); + if (root.val > val) return searchBST(root.left, val); + return null; +}; +``` + +> 迭代法 + +```typescript +function searchBST(root: TreeNode | null, val: number): TreeNode | null { + let resNode: TreeNode | null = root; + while (resNode !== null) { + if (resNode.val === val) return resNode; + if (resNode.val < val) { + resNode = resNode.right; + } else { + resNode = resNode.left; + } + } + return null; +}; +``` + ----------------------- From 7af58b92b86e045998ce3f7ceca186d73809cbdd Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Thu, 17 Feb 2022 15:07:13 +0800 Subject: [PATCH 28/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880098.=E9=AA=8C?= =?UTF-8?q?=E8=AF=81=E4=BA=8C=E5=8F=89=E6=90=9C=E7=B4=A2=E6=A0=91.md?= =?UTF-8?q?=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0typescript=E7=89=88?= =?UTF-8?q?=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0098.验证二叉搜索树.md | 42 ++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/problems/0098.验证二叉搜索树.md b/problems/0098.验证二叉搜索树.md index 4ed29619..c0f3e039 100644 --- a/problems/0098.验证二叉搜索树.md +++ b/problems/0098.验证二叉搜索树.md @@ -526,6 +526,48 @@ var isValidBST = function (root) { }; ``` +## TypeScript + +> 辅助数组解决: + +```typescript +function isValidBST(root: TreeNode | null): boolean { + const traversalArr: number[] = []; + function inorderTraverse(root: TreeNode | null): void { + if (root === null) return; + inorderTraverse(root.left); + traversalArr.push(root.val); + inorderTraverse(root.right); + } + inorderTraverse(root); + for (let i = 0, length = traversalArr.length; i < length - 1; i++) { + if (traversalArr[i] >= traversalArr[i + 1]) return false; + } + return true; +}; +``` + +> 递归中解决: + +```typescript +function isValidBST(root: TreeNode | null): boolean { + let maxVal = -Infinity; + function inorderTraverse(root: TreeNode | null): boolean { + if (root === null) return true; + let leftValid: boolean = inorderTraverse(root.left); + if (!leftValid) return false; + if (maxVal < root.val) { + maxVal = root.val + } else { + return false; + } + let rightValid: boolean = inorderTraverse(root.right); + return leftValid && rightValid; + } + return inorderTraverse(root); +}; +``` + ----------------------- From 6cb2076827726fc5be341e226585882424e523e7 Mon Sep 17 00:00:00 2001 From: hs-zhangsan <1513157458@qq.com> Date: Fri, 18 Feb 2022 17:03:41 +0800 Subject: [PATCH 29/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=20541.=E5=8F=8D?= =?UTF-8?q?=E8=BD=AC=E5=AD=97=E7=AC=A6=E4=B8=B2II=20C=E8=AF=AD=E8=A8=80?= =?UTF-8?q?=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0541.反转字符串II.md | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/problems/0541.反转字符串II.md b/problems/0541.反转字符串II.md index 14b8601a..bf59f52d 100644 --- a/problems/0541.反转字符串II.md +++ b/problems/0541.反转字符串II.md @@ -98,8 +98,31 @@ public: ## 其他语言版本 +C: + +```c +char * reverseStr(char * s, int k){ + int len = strlen(s); + + for (int i = 0; i < len; i += (2 * k)) { + //判断剩余字符是否少于 k + k = i + k > len ? len - i : k; + + int left = i; + int right = i + k - 1; + while (left < right) { + char temp = s[left]; + s[left++] = s[right]; + s[right--] = temp; + } + } + + return s; +} +``` Java: + ```Java //解法一 class Solution { From f5fe6bd73c936faedc52b93de3cd56ec39c0ec84 Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Fri, 18 Feb 2022 23:33:57 +0800 Subject: [PATCH 30/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=88530.=E4=BA=8C?= =?UTF-8?q?=E5=8F=89=E6=90=9C=E7=B4=A2=E6=A0=91=E7=9A=84=E6=9C=80=E5=B0=8F?= =?UTF-8?q?=E7=BB=9D=E5=AF=B9=E5=B7=AE=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?typescript=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../0530.二叉搜索树的最小绝对差.md | 71 ++++++++++++++++++- 1 file changed, 70 insertions(+), 1 deletion(-) diff --git a/problems/0530.二叉搜索树的最小绝对差.md b/problems/0530.二叉搜索树的最小绝对差.md index 3ebb4c8c..77699c9f 100644 --- a/problems/0530.二叉搜索树的最小绝对差.md +++ b/problems/0530.二叉搜索树的最小绝对差.md @@ -238,7 +238,7 @@ class Solution: cur = cur.right return result -``` +``` ## Go: @@ -364,5 +364,74 @@ var getMinimumDifference = function(root) { } ``` +## TypeScript + +> 辅助数组解决 + +```typescript +function getMinimumDifference(root: TreeNode | null): number { + let helperArr: number[] = []; + function recur(root: TreeNode | null): void { + if (root === null) return; + recur(root.left); + helperArr.push(root.val); + recur(root.right); + } + recur(root); + let resMin: number = Infinity; + for (let i = 0, length = helperArr.length; i < length - 1; i++) { + resMin = Math.min(resMin, helperArr[i + 1] - helperArr[i]); + } + return resMin; +}; +``` + +> 递归中解决 + +```typescript +function getMinimumDifference(root: TreeNode | null): number { + let preNode: TreeNode | null= null; + let resMin: number = Infinity; + function recur(root: TreeNode | null): void { + if (root === null) return; + recur(root.left); + if (preNode !== null) { + resMin = Math.min(resMin, root.val - preNode.val); + } + preNode = root; + recur(root.right); + } + recur(root); + return resMin; +}; +``` + +> 迭代法-中序遍历 + +```typescript +function getMinimumDifference(root: TreeNode | null): number { + const helperStack: TreeNode[] = []; + let curNode: TreeNode | null = root; + let resMin: number = Infinity; + let preNode: TreeNode | null = null; + while (curNode !== null || helperStack.length > 0) { + if (curNode !== null) { + helperStack.push(curNode); + curNode = curNode.left; + } else { + curNode = helperStack.pop()!; + if (preNode !== null) { + resMin = Math.min(resMin, curNode.val - preNode.val); + } + preNode = curNode; + curNode = curNode.right; + } + } + return resMin; +}; +``` + + + -----------------------
From 28cff716ac11f9f5970593fb42a38b399eae9490 Mon Sep 17 00:00:00 2001 From: bqlin Date: Tue, 21 Dec 2021 11:52:30 +0800 Subject: [PATCH 31/44] =?UTF-8?q?=E4=BA=8C=E5=8F=89=E6=A0=91=E7=9A=84?= =?UTF-8?q?=E9=80=92=E5=BD=92=E9=81=8D=E5=8E=86=EF=BC=9A=E4=BC=98=E5=8C=96?= =?UTF-8?q?=E6=8E=92=E7=89=88?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/二叉树的递归遍历.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/problems/二叉树的递归遍历.md b/problems/二叉树的递归遍历.md index c481fd11..9e131c6d 100644 --- a/problems/二叉树的递归遍历.md +++ b/problems/二叉树的递归遍历.md @@ -34,19 +34,19 @@ 1. **确定递归函数的参数和返回值**:因为要打印出前序遍历节点的数值,所以参数里需要传入vector在放节点的数值,除了这一点就不需要在处理什么数据了也不需要有返回值,所以递归函数返回类型就是void,代码如下: -``` +```cpp void traversal(TreeNode* cur, vector& vec) ``` 2. **确定终止条件**:在递归的过程中,如何算是递归结束了呢,当然是当前遍历的节点是空了,那么本层递归就要要结束了,所以如果当前遍历的这个节点是空,就直接return,代码如下: -``` +```cpp if (cur == NULL) return; ``` 3. **确定单层递归的逻辑**:前序遍历是中左右的循序,所以在单层递归的逻辑,是要先取中节点的数值,代码如下: -``` +```cpp vec.push_back(cur->val); // 中 traversal(cur->left, vec); // 左 traversal(cur->right, vec); // 右 From a9ae0f5d03b4e6f819c3c3d518f2984cf54d8810 Mon Sep 17 00:00:00 2001 From: bqlin Date: Tue, 21 Dec 2021 11:55:45 +0800 Subject: [PATCH 32/44] =?UTF-8?q?=E4=BA=8C=E5=8F=89=E6=A0=91=E7=9A=84?= =?UTF-8?q?=E8=BF=AD=E4=BB=A3=E9=81=8D=E5=8E=86=EF=BC=9A=E8=A1=A5=E5=85=85?= =?UTF-8?q?Swift=E5=AE=9E=E7=8E=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit # Conflicts: # problems/二叉树的迭代遍历.md --- problems/二叉树的迭代遍历.md | 104 ++++++++++++--------------- 1 file changed, 45 insertions(+), 59 deletions(-) diff --git a/problems/二叉树的迭代遍历.md b/problems/二叉树的迭代遍历.md index ba38726b..8164724b 100644 --- a/problems/二叉树的迭代遍历.md +++ b/problems/二叉树的迭代遍历.md @@ -390,7 +390,7 @@ func inorderTraversal(root *TreeNode) []int { } ``` -javaScript +javaScript: ```js @@ -454,7 +454,7 @@ var postorderTraversal = function(root, res = []) { }; ``` -TypeScript: +TypeScript: ```typescript // 前序遍历(迭代法) @@ -509,77 +509,63 @@ function postorderTraversal(root: TreeNode | null): number[] { }; ``` -Swift: +Swift: -> 迭代法前序遍历 ```swift +// 前序遍历迭代法 func preorderTraversal(_ root: TreeNode?) -> [Int] { - var res = [Int]() - if root == nil { - return res - } - var stack = [TreeNode]() - stack.append(root!) + var result = [Int]() + guard let root = root else { return result } + var stack = [root] while !stack.isEmpty { - let node = stack.popLast()! - res.append(node.val) - if node.right != nil { - stack.append(node.right!) + let current = stack.removeLast() + // 先右后左,这样出栈的时候才是左右顺序 + if let node = current.right { // 右 + stack.append(node) } - if node.left != nil { - stack.append(node.left!) + if let node = current.left { // 左 + stack.append(node) } + result.append(current.val) // 中 } - return res + return result } -``` -> 迭代法中序遍历 -```swift -func inorderTraversal(_ root: TreeNode?) -> [Int] { - var res = [Int]() - if root == nil { - return res - } - var stack = [TreeNode]() - var cur: TreeNode? = root - while cur != nil || !stack.isEmpty { - if cur != nil { - stack.append(cur!) - cur = cur!.left - } else { - cur = stack.popLast() - res.append(cur!.val) - cur = cur!.right - } - } - return res -} -``` - -> 迭代法后序遍历 -```swift +// 后序遍历迭代法 func postorderTraversal(_ root: TreeNode?) -> [Int] { - var res = [Int]() - if root == nil { - return res - } - var stack = [TreeNode]() - stack.append(root!) - // res 存储 中 -> 右 -> 左 + var result = [Int]() + guard let root = root else { return result } + var stack = [root] while !stack.isEmpty { - let node = stack.popLast()! - res.append(node.val) - if node.left != nil { - stack.append(node.left!) + let current = stack.removeLast() + // 与前序相反,即中右左,最后结果还需反转才是后序 + if let node = current.left { // 左 + stack.append(node) } - if node.right != nil { - stack.append(node.right!) + if let node = current.right { // 右 + stack.append(node) + } + result.append(current.val) // 中 + } + return result.reversed() +} + +// 中序遍历迭代法 +func inorderTraversal(_ root: TreeNode?) -> [Int] { + var result = [Int]() + var stack = [TreeNode]() + var current: TreeNode! = root + while current != nil || !stack.isEmpty { + if current != nil { // 先访问到最左叶子 + stack.append(current) + current = current.left // 左 + } else { + current = stack.removeLast() + result.append(current.val) // 中 + current = current.right // 右 } } - // res 翻转 - res.reverse() - return res + return result } ``` From af547486756b7213d17c10dd76c1a6e518a9b1fa Mon Sep 17 00:00:00 2001 From: bqlin Date: Tue, 21 Dec 2021 14:57:57 +0800 Subject: [PATCH 33/44] =?UTF-8?q?0102.=E4=BA=8C=E5=8F=89=E6=A0=91=E7=9A=84?= =?UTF-8?q?=E5=B1=82=E5=BA=8F=E9=81=8D=E5=8E=86=EF=BC=9A=E4=BC=98=E5=8C=96?= =?UTF-8?q?=E6=8E=92=E7=89=88=EF=BC=8C=E8=A1=A5=E5=85=85Swift=E7=89=88?= =?UTF-8?q?=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit # Conflicts: # problems/0102.二叉树的层序遍历.md --- problems/0102.二叉树的层序遍历.md | 332 ++++++++++------------ 1 file changed, 156 insertions(+), 176 deletions(-) diff --git a/problems/0102.二叉树的层序遍历.md b/problems/0102.二叉树的层序遍历.md index 1a92d42f..8d6d2502 100644 --- a/problems/0102.二叉树的层序遍历.md +++ b/problems/0102.二叉树的层序遍历.md @@ -273,32 +273,29 @@ function levelOrder(root: TreeNode | null): number[][] { }; ``` -Swift: +Swift: ```swift func levelOrder(_ root: TreeNode?) -> [[Int]] { - var res = [[Int]]() - guard let root = root else { - return res - } - var queue = [TreeNode]() - queue.append(root) + var result = [[Int]]() + guard let root = root else { return result } + // 表示一层 + var queue = [root] while !queue.isEmpty { - let size = queue.count - var sub = [Int]() - for _ in 0 ..< size { + let count = queue.count + var subarray = [Int]() + for _ in 0 ..< count { + // 当前层 let node = queue.removeFirst() - sub.append(node.val) - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) - } + subarray.append(node.val) + // 下一层 + if let node = node.left { queue.append(node) } + if let node = node.right { queue.append(node) } } - res.append(sub) + result.append(subarray) } - return res + + return result } ``` @@ -505,30 +502,29 @@ function levelOrderBottom(root: TreeNode | null): number[][] { }; ``` -Swift: +Swift: ```swift func levelOrderBottom(_ root: TreeNode?) -> [[Int]] { - var res = [[Int]]() - guard let root = root else { - return res - } - var queue: [TreeNode] = [root] + // 表示一层 + var queue = [TreeNode]() + if let node = root { queue.append(node) } + var result = [[Int]]() while !queue.isEmpty { - var sub = [Int]() - for _ in 0 ..< queue.count { + let count = queue.count + var subarray = [Int]() + for _ in 0 ..< count { + // 当前层 let node = queue.removeFirst() - sub.append(node.val) - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) - } + subarray.append(node.val) + // 下一层 + if let node = node.left { queue.append(node) } + if let node = node.right { queue.append(node)} } - res.insert(sub, at: 0) + result.append(subarray) } - return res + + return result.reversed() } ``` @@ -729,37 +725,31 @@ function rightSideView(root: TreeNode | null): number[] { }; ``` -Swift: +Swift: ```swift func rightSideView(_ root: TreeNode?) -> [Int] { - var res = [Int]() - guard let root = root else { - return res - } + // 表示一层 var queue = [TreeNode]() - queue.append(root) + if let node = root { queue.append(node) } + var result = [Int]() while !queue.isEmpty { - let size = queue.count - for i in 0 ..< size { + let count = queue.count + for i in 0 ..< count { + // 当前层 let node = queue.removeFirst() - if i == size - 1 { - // 保存 每层最后一个元素 - res.append(node.val) - } - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) - } + if i == count - 1 { result.append(node.val) } + + // 下一层 + if let node = node.left { queue.append(node) } + if let node = node.right { queue.append(node) } } } - return res + + return result } ``` - # 637.二叉树的层平均值 [力扣题目链接](https://leetcode-cn.com/problems/average-of-levels-in-binary-tree/) @@ -965,32 +955,30 @@ function averageOfLevels(root: TreeNode | null): number[] { }; ``` -Swift: +Swift: ```swift func averageOfLevels(_ root: TreeNode?) -> [Double] { - var res = [Double]() - guard let root = root else { - return res - } + // 表示一层 var queue = [TreeNode]() - queue.append(root) + if let node = root { queue.append(node) } + var result = [Double]() while !queue.isEmpty { - let size = queue.count + let count = queue.count var sum = 0 - for _ in 0 ..< size { + for _ in 0 ..< count { + // 当前层 let node = queue.removeFirst() sum += node.val - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) - } + + // 下一层 + if let node = node.left { queue.append(node) } + if let node = node.right { queue.append(node) } } - res.append(Double(sum) / Double(size)) + result.append(Double(sum) / Double(count)) } - return res + + return result } ``` @@ -1212,29 +1200,28 @@ function levelOrder(root: Node | null): number[][] { }; ``` -Swift: +Swift: ```swift func levelOrder(_ root: Node?) -> [[Int]] { - var res = [[Int]]() - guard let root = root else { - return res - } + // 表示一层 var queue = [Node]() - queue.append(root) + if let node = root { queue.append(node) } + var result = [[Int]]() while !queue.isEmpty { - let size = queue.count - var sub = [Int]() - for _ in 0 ..< size { + let count = queue.count + var subarray = [Int]() + for _ in 0 ..< count { + // 当前层 let node = queue.removeFirst() - sub.append(node.val) - for childNode in node.children { - queue.append(childNode) - } + subarray.append(node.val) + // 下一层 + for node in node.children { queue.append(node) } } - res.append(sub) + result.append(subarray) } - return res + + return result } ``` @@ -1419,34 +1406,30 @@ function largestValues(root: TreeNode | null): number[] { }; ``` -Swift: +Swift: ```swift func largestValues(_ root: TreeNode?) -> [Int] { - var res = [Int]() - guard let root = root else { - return res - } + // 表示一层 var queue = [TreeNode]() - queue.append(root) + if let node = root { queue.append(node) } + var result = [Int]() while !queue.isEmpty { - let size = queue.count - var max: Int = Int.min - for _ in 0 ..< size { + let count = queue.count + var max = queue[0].val + for _ in 0 ..< count { + // 当前层 let node = queue.removeFirst() - if node.val > max { - max = node.val - } - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) - } + if node.val > max { max = node.val } + + // 下一层 + if let node = node.left { queue.append(node) } + if let node = node.right { queue.append(node) } } - res.append(max) + result.append(max) } - return res + + return result } ``` @@ -1456,7 +1439,7 @@ func largestValues(_ root: TreeNode?) -> [Int] { 给定一个完美二叉树,其所有叶子节点都在同一层,每个父节点都有两个子节点。二叉树定义如下: -``` +```cpp struct Node { int val; Node *left; @@ -1677,33 +1660,34 @@ func connect(root *Node) *Node { } ``` -Swift: +Swift: + ```swift func connect(_ root: Node?) -> Node? { - guard let root = root else { - return nil - } + // 表示一层 var queue = [Node]() - queue.append(root) + if let node = root { queue.append(node) } while !queue.isEmpty { - let size = queue.count - var preNode: Node? - for i in 0 ..< size { - let node = queue.removeFirst() + let count = queue.count + var current, previous: Node! + for i in 0 ..< count { + // 当前层 if i == 0 { - preNode = node + previous = queue.removeFirst() + current = previous } else { - preNode?.next = node - preNode = node - } - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) + current = queue.removeFirst() + previous.next = current + previous = current } + + // 下一层 + if let node = current.left { queue.append(node) } + if let node = current.right { queue.append(node) } } + previous.next = nil } + return root } ``` @@ -1927,34 +1911,34 @@ func connect(root *Node) *Node { return root } ``` - Swift: + ```swift func connect(_ root: Node?) -> Node? { - guard let root = root else { - return nil - } + // 表示一层 var queue = [Node]() - queue.append(root) + if let node = root { queue.append(node) } while !queue.isEmpty { - let size = queue.count - var preNode: Node? - for i in 0 ..< size { - let node = queue.removeFirst() + let count = queue.count + var current, previous: Node! + for i in 0 ..< count { + // 当前层 if i == 0 { - preNode = node + previous = queue.removeFirst() + current = previous } else { - preNode?.next = node - preNode = node - } - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) + current = queue.removeFirst() + previous.next = current + previous = current } + + // 下一层 + if let node = current.left { queue.append(node) } + if let node = current.right { queue.append(node) } } + previous.next = nil } + return root } ``` @@ -2151,29 +2135,28 @@ function maxDepth(root: TreeNode | null): number { }; ``` -Swift: +Swift: ```swift func maxDepth(_ root: TreeNode?) -> Int { - guard let root = root else { - return 0 - } + guard root != nil else { return 0 } + var depth = 0 var queue = [TreeNode]() - queue.append(root) - var res: Int = 0 + queue.append(root!) while !queue.isEmpty { - for _ in 0 ..< queue.count { + let count = queue.count + depth += 1 + for _ in 0 ..< count { + // 当前层 let node = queue.removeFirst() - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) - } + + // 下一层 + if let node = node.left { queue.append(node) } + if let node = node.right { queue.append(node) } } - res += 1 } - return res + + return depth } ``` @@ -2374,28 +2357,25 @@ Swift: ```swift func minDepth(_ root: TreeNode?) -> Int { - guard let root = root else { - return 0 - } - var res = 0 - var queue = [TreeNode]() - queue.append(root) + guard root != nil else { return 0 } + var depth = 0 + var queue = [root!] while !queue.isEmpty { - res += 1 - for _ in 0 ..< queue.count { + let count = queue.count + depth += 1 + for _ in 0 ..< count { + // 当前层 let node = queue.removeFirst() - if node.left == nil && node.right == nil { - return res - } - if let left = node.left { - queue.append(left) - } - if let right = node.right { - queue.append(right) + if node.left == nil, node.right == nil { // 遇到叶子结点则返回 + return depth } + + // 下一层 + if let node = node.left { queue.append(node) } + if let node = node.right { queue.append(node) } } } - return res + return depth } ``` From 53d4999ad8e7b16a790a8cfcdb6a0f030ec96dfd Mon Sep 17 00:00:00 2001 From: bqlin Date: Sat, 25 Dec 2021 17:14:15 +0800 Subject: [PATCH 34/44] =?UTF-8?q?0226.=E7=BF=BB=E8=BD=AC=E4=BA=8C=E5=8F=89?= =?UTF-8?q?=E6=A0=91=EF=BC=9A=E4=BC=98=E5=8C=96=E6=8E=92=E7=89=88=EF=BC=8C?= =?UTF-8?q?=E8=A1=A5=E5=85=85Swift=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit # Conflicts: # problems/0226.翻转二叉树.md --- problems/0226.翻转二叉树.md | 63 +++++++++++++++++++++++++++----- 1 file changed, 54 insertions(+), 9 deletions(-) diff --git a/problems/0226.翻转二叉树.md b/problems/0226.翻转二叉树.md index 8108e7ad..a3ebe24d 100644 --- a/problems/0226.翻转二叉树.md +++ b/problems/0226.翻转二叉树.md @@ -47,8 +47,6 @@ ## 递归法 - - 对于二叉树的递归法的前中后序遍历,已经在[二叉树:前中后序递归遍历](https://programmercarl.com/二叉树的递归遍历.html)详细讲解了。 我们下文以前序遍历为例,通过动画来看一下翻转的过程: @@ -63,7 +61,7 @@ 返回值的话其实也不需要,但是题目中给出的要返回root节点的指针,可以直接使用题目定义好的函数,所以就函数的返回类型为`TreeNode*`。 -``` +```cpp TreeNode* invertTree(TreeNode* root) ``` @@ -71,7 +69,7 @@ TreeNode* invertTree(TreeNode* root) 当前节点为空的时候,就返回 -``` +```cpp if (root == NULL) return root; ``` @@ -79,7 +77,7 @@ if (root == NULL) return root; 因为是先前序遍历,所以先进行交换左右孩子节点,然后反转左子树,反转右子树。 -``` +```cpp swap(root->left, root->right); invertTree(root->left); invertTree(root->right); @@ -257,7 +255,7 @@ public: ## 其他语言版本 -### Java: +### Java ```Java //DFS递归 @@ -469,8 +467,6 @@ func invertTree(root *TreeNode) *TreeNode { } ``` - - ### JavaScript 使用递归版本的前序遍历 @@ -690,7 +686,7 @@ function invertTree(root: TreeNode | null): TreeNode | null { }; ``` -### C: +### C 递归法 ```c @@ -775,5 +771,54 @@ func invertTree1(_ root: TreeNode?) -> TreeNode? { } ``` +### Swift + +深度优先递归。 + +```swift +func invertTree(_ root: TreeNode?) -> TreeNode? { + guard let node = root else { return root } + swap(&node.left, &node.right) + _ = invertTree(node.left) + _ = invertTree(node.right) + return root +} +``` + +深度优先迭代,子结点顺序不重要,从根结点出发深度遍历即可。 + +```swift +func invertTree(_ root: TreeNode?) -> TreeNode? { + guard let node = root else { return root } + var stack = [node] + while !stack.isEmpty { + guard let node = stack.popLast() else { break } + swap(&node.left, &node.right) + if let node = node.left { stack.append(node) } + if let node = node.right { stack.append(node) } + } + return root +} +``` + +广度优先迭代。 + +```swift +func invertTree(_ root: TreeNode?) -> TreeNode? { + guard let node = root else { return root } + var queue = [node] + while !queue.isEmpty { + let count = queue.count + for _ in 0 ..< count { + let node = queue.removeFirst() + swap(&node.left, &node.right) + if let node = node.left { queue.append(node) } + if let node = node.right { queue.append(node) } + } + } + return root +} +``` + -----------------------
From 9b991d89948d5793f1f93cedb7d0c2093586506e Mon Sep 17 00:00:00 2001 From: Steve2020 <841532108@qq.com> Date: Sat, 19 Feb 2022 15:05:26 +0800 Subject: [PATCH 35/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=EF=BC=880501.=E4=BA=8C?= =?UTF-8?q?=E5=8F=89=E6=90=9C=E7=B4=A2=E6=A0=91=E4=B8=AD=E7=9A=84=E4=BC=97?= =?UTF-8?q?=E6=95=B0.md=EF=BC=89=EF=BC=9A=E5=A2=9E=E5=8A=A0typescript?= =?UTF-8?q?=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0501.二叉搜索树中的众数.md | 105 ++++++++++++++++++- 1 file changed, 103 insertions(+), 2 deletions(-) diff --git a/problems/0501.二叉搜索树中的众数.md b/problems/0501.二叉搜索树中的众数.md index 277f46f5..1be9ee6a 100644 --- a/problems/0501.二叉搜索树中的众数.md +++ b/problems/0501.二叉搜索树中的众数.md @@ -512,7 +512,7 @@ class Solution: self.search_BST(cur.right) ``` - + > 迭代法-中序遍历-不使用额外空间,利用二叉搜索树特性 ```python3 @@ -661,7 +661,7 @@ var findMode = function(root) { } return res; }; -``` +``` 不使用额外空间,利用二叉树性质,中序遍历(有序): @@ -699,6 +699,107 @@ var findMode = function(root) { }; ``` +## TypeScript + +> 辅助Map法 + +```typescript +function findMode(root: TreeNode | null): number[] { + if (root === null) return []; + const countMap: Map = new Map(); + function traverse(root: TreeNode | null): void { + if (root === null) return; + countMap.set(root.val, (countMap.get(root.val) || 0) + 1); + traverse(root.left); + traverse(root.right); + } + traverse(root); + const countArr: number[][] = Array.from(countMap); + countArr.sort((a, b) => { + return b[1] - a[1]; + }) + const resArr: number[] = []; + const maxCount: number = countArr[0][1]; + for (let i of countArr) { + if (i[1] === maxCount) resArr.push(i[0]); + } + return resArr; +}; +``` + +> 递归中直接解决 + +```typescript +function findMode(root: TreeNode | null): number[] { + let preNode: TreeNode | null = null; + let maxCount: number = 0; + let count: number = 0; + let resArr: number[] = []; + function traverse(root: TreeNode | null): void { + if (root === null) return; + traverse(root.left); + if (preNode === null) { // 第一个节点 + count = 1; + } else if (preNode.val === root.val) { + count++; + } else { + count = 1; + } + if (count === maxCount) { + resArr.push(root.val); + } else if (count > maxCount) { + maxCount = count; + resArr.length = 0; + resArr.push(root.val); + } + preNode = root; + traverse(root.right); + } + traverse(root); + return resArr; +}; +``` + +> 迭代法 + +```typescript +function findMode(root: TreeNode | null): number[] { + const helperStack: TreeNode[] = []; + const resArr: number[] = []; + let maxCount: number = 0; + let count: number = 0; + let preNode: TreeNode | null = null; + let curNode: TreeNode | null = root; + while (curNode !== null || helperStack.length > 0) { + if (curNode !== null) { + helperStack.push(curNode); + curNode = curNode.left; + } else { + curNode = helperStack.pop()!; + if (preNode === null) { // 第一个节点 + count = 1; + } else if (preNode.val === curNode.val) { + count++; + } else { + count = 1; + } + if (count === maxCount) { + resArr.push(curNode.val); + } else if (count > maxCount) { + maxCount = count; + resArr.length = 0; + resArr.push(curNode.val); + } + preNode = curNode; + curNode = curNode.right; + } + } + return resArr; +}; +``` + + + -----------------------
From 292fe1eb380622ce4fc19f2d05ef26bb472e855d Mon Sep 17 00:00:00 2001 From: hs-zhangsan <1513157458@qq.com> Date: Sat, 19 Feb 2022 15:55:31 +0800 Subject: [PATCH 36/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=20=E5=89=91=E6=8C=87Of?= =?UTF-8?q?fer=2005.=E6=9B=BF=E6=8D=A2=E7=A9=BA=E6=A0=BC=20C=E8=AF=AD?= =?UTF-8?q?=E8=A8=80=E7=89=88=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/剑指Offer05.替换空格.md | 31 ++++++++++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/problems/剑指Offer05.替换空格.md b/problems/剑指Offer05.替换空格.md index 530545fb..9e743887 100644 --- a/problems/剑指Offer05.替换空格.md +++ b/problems/剑指Offer05.替换空格.md @@ -121,6 +121,37 @@ for (int i = 0; i < a.size(); i++) { ## 其他语言版本 +C: +```C +char* replaceSpace(char* s){ + //统计空格数量 + int count = 0; + int len = strlen(s); + for (int i = 0; i < len; i++) { + if (s[i] == ' ') { + count++; + } + } + + //为新数组分配空间 + int newLen = len + count * 2; + char* result = malloc(sizeof(char) * newLen + 1); + //填充新数组并替换空格 + for (int i = len - 1, j = newLen - 1; i >= 0; i--, j--) { + if (s[i] != ' ') { + result[j] = s[i]; + } else { + result[j--] = '0'; + result[j--] = '2'; + result[j] = '%'; + } + } + result[newLen] = '\0'; + + return result; +} +``` + Java: ```Java From bb277e08e19b797a1b5da5bfe0c60ef84b5c9c8e Mon Sep 17 00:00:00 2001 From: K-945 <393763635@qq.com> Date: Sun, 20 Feb 2022 17:56:21 +0800 Subject: [PATCH 37/44] =?UTF-8?q?=E6=B7=BB=E5=8A=A00059.=E8=9E=BA=E6=97=8B?= =?UTF-8?q?=E7=9F=A9=E9=98=B5II.md=20=E5=92=8C=E8=A7=A3=E6=9E=90=E7=9B=B8?= =?UTF-8?q?=E5=90=8C=E7=9A=84python=E7=89=88?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0059.螺旋矩阵II.md | 60 ++++++++++++--------------------- 1 file changed, 22 insertions(+), 38 deletions(-) diff --git a/problems/0059.螺旋矩阵II.md b/problems/0059.螺旋矩阵II.md index 3f7a59ca..a98e72ad 100644 --- a/problems/0059.螺旋矩阵II.md +++ b/problems/0059.螺旋矩阵II.md @@ -192,47 +192,31 @@ python: ```python3 class Solution: - def generateMatrix(self, n: int) -> List[List[int]]: - # 初始化要填充的正方形 - matrix = [[0] * n for _ in range(n)] + nums = [[0] * n for _ in range(n)] + startx, starty = 0, 0 # 起始点 + loop, mid = n // 2, n // 2 # 迭代次数、n为奇数时,矩阵的中心点 + count = 1 # 计数 - left, right, up, down = 0, n - 1, 0, n - 1 - number = 1 # 要填充的数字 + for offset in range(1, loop + 1) : # 每循环一层偏移量加1,偏移量从1开始 + for i in range(starty, n - offset) : # 从左至右,左闭右开 + nums[startx][i] = count + count += 1 + for i in range(startx, n - offset) : # 从上至下 + nums[i][n - offset] = count + count += 1 + for i in range(n - offset, starty, -1) : # 从右至左 + nums[n - offset][i] = count + count += 1 + for i in range(n - offset, startx, -1) : # 从下至上 + nums[i][starty] = count + count += 1 + startx += 1 # 更新起始点 + starty += 1 - while left < right and up < down: - - # 从左到右填充上边 - for x in range(left, right): - matrix[up][x] = number - number += 1 - - # 从上到下填充右边 - for y in range(up, down): - matrix[y][right] = number - number += 1 - - # 从右到左填充下边 - for x in range(right, left, -1): - matrix[down][x] = number - number += 1 - - # 从下到上填充左边 - for y in range(down, up, -1): - matrix[y][left] = number - number += 1 - - # 缩小要填充的范围 - left += 1 - right -= 1 - up += 1 - down -= 1 - - # 如果阶数为奇数,额外填充一次中心 - if n % 2: - matrix[n // 2][n // 2] = number - - return matrix + if n % 2 != 0 : # n为奇数时,填充中心点 + nums[mid][mid] = count + return nums ``` javaScript From 3652d00e542fc251d479a66eb676c8e1ac910f45 Mon Sep 17 00:00:00 2001 From: Luo <82520819+Jerry-306@users.noreply.github.com> Date: Thu, 24 Feb 2022 17:49:15 +0800 Subject: [PATCH 38/44] =?UTF-8?q?0104=20=E4=BA=8C=E5=8F=89=E6=A0=91?= =?UTF-8?q?=E6=9C=80=E5=A4=A7=E6=B7=B1=E5=BA=A6=20=E9=83=A8=E5=88=86?= =?UTF-8?q?=E4=BB=A3=E7=A0=81=E4=B9=A6=E5=86=99=E9=94=99=E8=AF=AF=E7=BA=A0?= =?UTF-8?q?=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 函数错误,逻辑错误 --- problems/0104.二叉树的最大深度.md | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/problems/0104.二叉树的最大深度.md b/problems/0104.二叉树的最大深度.md index 3eecdc92..2229a854 100644 --- a/problems/0104.二叉树的最大深度.md +++ b/problems/0104.二叉树的最大深度.md @@ -523,8 +523,8 @@ func maxdepth(root *treenode) int { ```javascript var maxdepth = function(root) { - if (!root) return root - return 1 + math.max(maxdepth(root.left), maxdepth(root.right)) + if (root === null) return 0; + return 1 + Math.max(maxdepth(root.left), maxdepth(root.right)) }; ``` @@ -541,7 +541,7 @@ var maxdepth = function(root) { //3. 确定单层逻辑 let leftdepth=getdepth(node.left); let rightdepth=getdepth(node.right); - let depth=1+math.max(leftdepth,rightdepth); + let depth=1+Math.max(leftdepth,rightdepth); return depth; } return getdepth(root); @@ -591,7 +591,9 @@ var maxDepth = function(root) { count++ while(size--) { let node = queue.shift() - node && (queue = [...queue, ...node.children]) + for (let item of node.children) { + item && queue.push(item); + } } } return count From 14f91a53702d8df5e1a587e757f739b5df55bb8f Mon Sep 17 00:00:00 2001 From: Luo <82520819+Jerry-306@users.noreply.github.com> Date: Fri, 25 Feb 2022 10:37:17 +0800 Subject: [PATCH 39/44] =?UTF-8?q?0404=20=E5=B7=A6=E5=8F=B6=E5=AD=90?= =?UTF-8?q?=E4=B9=8B=E5=92=8C=20=20=E5=B7=A6=E5=8F=B6=E5=AD=90=E5=AE=9A?= =?UTF-8?q?=E4=B9=89=E9=94=99=E8=AF=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- problems/0404.左叶子之和.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/problems/0404.左叶子之和.md b/problems/0404.左叶子之和.md index 09272052..691c0f37 100644 --- a/problems/0404.左叶子之和.md +++ b/problems/0404.左叶子之和.md @@ -19,7 +19,7 @@ **首先要注意是判断左叶子,不是二叉树左侧节点,所以不要上来想着层序遍历。** -因为题目中其实没有说清楚左叶子究竟是什么节点,那么我来给出左叶子的明确定义:**如果左节点不为空,且左节点没有左右孩子,那么这个节点就是左叶子** +因为题目中其实没有说清楚左叶子究竟是什么节点,那么我来给出左叶子的明确定义:**如果左节点不为空,且左节点没有左右孩子,那么这个节点的左节点就是左叶子** 大家思考一下如下图中二叉树,左叶子之和究竟是多少? From 37e7d73ec200bd9adefbdaaef24d6f4c2e38f5f7 Mon Sep 17 00:00:00 2001 From: youngyangyang04 <826123027@qq.com> Date: Mon, 28 Feb 2022 20:52:01 +0800 Subject: [PATCH 40/44] Update --- problems/0020.有效的括号.md | 4 ++-- problems/0027.移除元素.md | 2 +- problems/0035.搜索插入位置.md | 2 +- problems/0039.组合总和.md | 4 ++-- problems/0040.组合总和II.md | 4 ++-- problems/0042.接雨水.md | 2 +- problems/0046.全排列.md | 2 +- problems/0059.螺旋矩阵II.md | 4 ++-- problems/0070.爬楼梯完全背包版本.md | 4 ++-- problems/0077.组合优化.md | 2 +- problems/0078.子集.md | 2 +- problems/0084.柱状图中最大的矩形.md | 4 ++-- problems/0093.复原IP地址.md | 2 +- problems/0102.二叉树的层序遍历.md | 4 ++-- .../0108.将有序数组转换为二叉搜索树.md | 2 +- problems/0110.平衡二叉树.md | 2 +- problems/0129.求根到叶子节点数字之和.md | 2 +- problems/0131.分割回文串.md | 4 ++-- problems/0188.买卖股票的最佳时机IV.md | 2 +- problems/0257.二叉树的所有路径.md | 2 +- problems/0279.完全平方数.md | 2 +- problems/0322.零钱兑换.md | 2 +- problems/0337.打家劫舍III.md | 6 +++--- problems/0376.摆动序列.md | 2 +- problems/0383.赎金信.md | 2 +- problems/0404.左叶子之和.md | 4 ++-- problems/0455.分发饼干.md | 2 +- problems/0463.岛屿的周长.md | 2 +- problems/0474.一和零.md | 2 +- problems/0491.递增子序列.md | 4 ++-- problems/0494.目标和.md | 11 ++++++++--- problems/0496.下一个更大元素I.md | 4 ++-- problems/0501.二叉搜索树中的众数.md | 4 ++-- problems/0503.下一个更大元素II.md | 2 +- problems/0518.零钱兑换II.md | 2 +- problems/0538.把二叉搜索树转换为累加树.md | 2 +- problems/0669.修剪二叉搜索树.md | 2 +- problems/0841.钥匙和房间.md | 1 - ...1047.删除字符串中的所有相邻重复项.md | 4 ++-- problems/二叉树的递归遍历.md | 2 +- problems/周总结/20201003二叉树周末总结.md | 4 ++-- problems/背包问题理论基础完全背包.md | 2 +- 42 files changed, 64 insertions(+), 60 deletions(-) diff --git a/problems/0020.有效的括号.md b/problems/0020.有效的括号.md index 95d62e42..01fc7b93 100644 --- a/problems/0020.有效的括号.md +++ b/problems/0020.有效的括号.md @@ -159,7 +159,7 @@ class Solution { ``` Python: -```python3 +```python # 方法一,仅使用栈,更省空间 class Solution: def isValid(self, s: str) -> bool: @@ -180,7 +180,7 @@ class Solution: return True if not stack else False ``` -```python3 +```python # 方法二,使用字典 class Solution: def isValid(self, s: str) -> bool: diff --git a/problems/0027.移除元素.md b/problems/0027.移除元素.md index d69f2bcf..dd9155c6 100644 --- a/problems/0027.移除元素.md +++ b/problems/0027.移除元素.md @@ -142,7 +142,7 @@ class Solution { Python: -```python3 +```python class Solution: """双指针法 时间复杂度:O(n) diff --git a/problems/0035.搜索插入位置.md b/problems/0035.搜索插入位置.md index f5f041aa..9a770703 100644 --- a/problems/0035.搜索插入位置.md +++ b/problems/0035.搜索插入位置.md @@ -246,7 +246,7 @@ func searchInsert(nums []int, target int) int { ``` ### Python -```python3 +```python class Solution: def searchInsert(self, nums: List[int], target: int) -> int: left, right = 0, len(nums) - 1 diff --git a/problems/0039.组合总和.md b/problems/0039.组合总和.md index 0f8fe4f6..7a2084dd 100644 --- a/problems/0039.组合总和.md +++ b/problems/0039.组合总和.md @@ -264,7 +264,7 @@ class Solution { ## Python **回溯** -```python3 +```python class Solution: def __init__(self): self.path = [] @@ -296,7 +296,7 @@ class Solution: self.path.pop() # 回溯 ``` **剪枝回溯** -```python3 +```python class Solution: def __init__(self): self.path = [] diff --git a/problems/0040.组合总和II.md b/problems/0040.组合总和II.md index 54384188..49acb8d6 100644 --- a/problems/0040.组合总和II.md +++ b/problems/0040.组合总和II.md @@ -334,7 +334,7 @@ class Solution { ## Python **回溯+巧妙去重(省去使用used** -```python3 +```python class Solution: def __init__(self): self.paths = [] @@ -374,7 +374,7 @@ class Solution: sum_ -= candidates[i] # 回溯,为了下一轮for loop ``` **回溯+去重(使用used)** -```python3 +```python class Solution: def __init__(self): self.paths = [] diff --git a/problems/0042.接雨水.md b/problems/0042.接雨水.md index 27745607..55f80a54 100644 --- a/problems/0042.接雨水.md +++ b/problems/0042.接雨水.md @@ -491,7 +491,7 @@ class Solution: return res ``` 动态规划 -```python3 +```python class Solution: def trap(self, height: List[int]) -> int: leftheight, rightheight = [0]*len(height), [0]*len(height) diff --git a/problems/0046.全排列.md b/problems/0046.全排列.md index 3d31db62..c5369ddd 100644 --- a/problems/0046.全排列.md +++ b/problems/0046.全排列.md @@ -243,7 +243,7 @@ class Solution: usage_list[i] = False ``` **回溯+丢掉usage_list** -```python3 +```python class Solution: def __init__(self): self.path = [] diff --git a/problems/0059.螺旋矩阵II.md b/problems/0059.螺旋矩阵II.md index 3f7a59ca..670d6fc2 100644 --- a/problems/0059.螺旋矩阵II.md +++ b/problems/0059.螺旋矩阵II.md @@ -188,9 +188,9 @@ class Solution { } ``` -python: +python3: -```python3 +```python class Solution: def generateMatrix(self, n: int) -> List[List[int]]: diff --git a/problems/0070.爬楼梯完全背包版本.md b/problems/0070.爬楼梯完全背包版本.md index b5fbb96a..2286de2d 100644 --- a/problems/0070.爬楼梯完全背包版本.md +++ b/problems/0070.爬楼梯完全背包版本.md @@ -143,10 +143,10 @@ class Solution { } ``` -Python: +Python3: -```python3 +```python class Solution: def climbStairs(self, n: int) -> int: dp = [0]*(n + 1) diff --git a/problems/0077.组合优化.md b/problems/0077.组合优化.md index e995fd18..81b4304c 100644 --- a/problems/0077.组合优化.md +++ b/problems/0077.组合优化.md @@ -174,7 +174,7 @@ class Solution { ``` Python: -```python3 +```python class Solution: def combine(self, n: int, k: int) -> List[List[int]]: res=[] #存放符合条件结果的集合 diff --git a/problems/0078.子集.md b/problems/0078.子集.md index 1abf8c95..cdb5f548 100644 --- a/problems/0078.子集.md +++ b/problems/0078.子集.md @@ -203,7 +203,7 @@ class Solution { ``` ## Python -```python3 +```python class Solution: def __init__(self): self.path: List[int] = [] diff --git a/problems/0084.柱状图中最大的矩形.md b/problems/0084.柱状图中最大的矩形.md index 3cb51f1d..439a3bc5 100644 --- a/problems/0084.柱状图中最大的矩形.md +++ b/problems/0084.柱状图中最大的矩形.md @@ -277,9 +277,9 @@ class Solution { } ``` -Python: +Python3: -```python3 +```python # 双指针;暴力解法(leetcode超时) class Solution: diff --git a/problems/0093.复原IP地址.md b/problems/0093.复原IP地址.md index 3e7cd1ad..1fa72cc9 100644 --- a/problems/0093.复原IP地址.md +++ b/problems/0093.复原IP地址.md @@ -339,7 +339,7 @@ class Solution(object): ``` python3: -```python3 +```python class Solution: def __init__(self): self.result = [] diff --git a/problems/0102.二叉树的层序遍历.md b/problems/0102.二叉树的层序遍历.md index 1a92d42f..74485848 100644 --- a/problems/0102.二叉树的层序遍历.md +++ b/problems/0102.二叉树的层序遍历.md @@ -83,10 +83,10 @@ public: }; ``` -python代码: +python3代码: -```python3 +```python class Solution: """二叉树层序遍历迭代解法""" diff --git a/problems/0108.将有序数组转换为二叉搜索树.md b/problems/0108.将有序数组转换为二叉搜索树.md index bd48ea0c..9e008e86 100644 --- a/problems/0108.将有序数组转换为二叉搜索树.md +++ b/problems/0108.将有序数组转换为二叉搜索树.md @@ -305,7 +305,7 @@ class Solution { ## Python **递归** -```python3 +```python # Definition for a binary tree node. # class TreeNode: # def __init__(self, val=0, left=None, right=None): diff --git a/problems/0110.平衡二叉树.md b/problems/0110.平衡二叉树.md index 90cb7336..d9dcf289 100644 --- a/problems/0110.平衡二叉树.md +++ b/problems/0110.平衡二叉树.md @@ -497,7 +497,7 @@ class Solution { ## Python 递归法: -```python3 +```python # Definition for a binary tree node. # class TreeNode: # def __init__(self, val=0, left=None, right=None): diff --git a/problems/0129.求根到叶子节点数字之和.md b/problems/0129.求根到叶子节点数字之和.md index 980779c2..b271ca7d 100644 --- a/problems/0129.求根到叶子节点数字之和.md +++ b/problems/0129.求根到叶子节点数字之和.md @@ -217,7 +217,7 @@ class Solution { ``` Python: -```python3 +```python class Solution: def sumNumbers(self, root: TreeNode) -> int: res = 0 diff --git a/problems/0131.分割回文串.md b/problems/0131.分割回文串.md index 439ad8ea..f50f1c1d 100644 --- a/problems/0131.分割回文串.md +++ b/problems/0131.分割回文串.md @@ -289,7 +289,7 @@ class Solution { ## Python **回溯+正反序判断回文串** -```python3 +```python class Solution: def __init__(self): self.paths = [] @@ -326,7 +326,7 @@ class Solution: continue ``` **回溯+函数判断回文串** -```python3 +```python class Solution: def __init__(self): self.paths = [] diff --git a/problems/0188.买卖股票的最佳时机IV.md b/problems/0188.买卖股票的最佳时机IV.md index 7db75f06..61c558a1 100644 --- a/problems/0188.买卖股票的最佳时机IV.md +++ b/problems/0188.买卖股票的最佳时机IV.md @@ -271,7 +271,7 @@ class Solution: return dp[-1][2*k] ``` 版本二 -```python3 +```python class Solution: def maxProfit(self, k: int, prices: List[int]) -> int: if len(prices) == 0: return 0 diff --git a/problems/0257.二叉树的所有路径.md b/problems/0257.二叉树的所有路径.md index 4078320f..a0c718f4 100644 --- a/problems/0257.二叉树的所有路径.md +++ b/problems/0257.二叉树的所有路径.md @@ -436,7 +436,7 @@ class Solution: 迭代法: -```python3 +```python from collections import deque diff --git a/problems/0279.完全平方数.md b/problems/0279.完全平方数.md index 7bc0c2f7..9bad2085 100644 --- a/problems/0279.完全平方数.md +++ b/problems/0279.完全平方数.md @@ -207,7 +207,7 @@ class Solution { Python: -```python3 +```python class Solution: def numSquares(self, n: int) -> int: '''版本一,先遍历背包, 再遍历物品''' diff --git a/problems/0322.零钱兑换.md b/problems/0322.零钱兑换.md index 8f3438af..3a8d0662 100644 --- a/problems/0322.零钱兑换.md +++ b/problems/0322.零钱兑换.md @@ -207,7 +207,7 @@ class Solution { Python: -```python3 +```python class Solution: def coinChange(self, coins: List[int], amount: int) -> int: '''版本一''' diff --git a/problems/0337.打家劫舍III.md b/problems/0337.打家劫舍III.md index 06831cb6..ecd31d1b 100644 --- a/problems/0337.打家劫舍III.md +++ b/problems/0337.打家劫舍III.md @@ -288,7 +288,7 @@ Python: > 暴力递归 -```python3 +```python # Definition for a binary tree node. # class TreeNode: @@ -315,7 +315,7 @@ class Solution: > 记忆化递归 -```python3 +```python # Definition for a binary tree node. # class TreeNode: @@ -345,7 +345,7 @@ class Solution: ``` > 动态规划 -```python3 +```python # Definition for a binary tree node. # class TreeNode: # def __init__(self, val=0, left=None, right=None): diff --git a/problems/0376.摆动序列.md b/problems/0376.摆动序列.md index d75311eb..5076c9ad 100644 --- a/problems/0376.摆动序列.md +++ b/problems/0376.摆动序列.md @@ -228,7 +228,7 @@ class Solution { ### Python -```python3 +```python class Solution: def wiggleMaxLength(self, nums: List[int]) -> int: preC,curC,res = 0,0,1 #题目里nums长度大于等于1,当长度为1时,其实到不了for循环里去,所以不用考虑nums长度 diff --git a/problems/0383.赎金信.md b/problems/0383.赎金信.md index 31e19b10..00707347 100644 --- a/problems/0383.赎金信.md +++ b/problems/0383.赎金信.md @@ -209,7 +209,7 @@ class Solution(object): Python写法四: -```python3 +```python class Solution: def canConstruct(self, ransomNote: str, magazine: str) -> bool: c1 = collections.Counter(ransomNote) diff --git a/problems/0404.左叶子之和.md b/problems/0404.左叶子之和.md index 09272052..8c6eaddb 100644 --- a/problems/0404.左叶子之和.md +++ b/problems/0404.左叶子之和.md @@ -229,7 +229,7 @@ class Solution { ## Python **递归后序遍历** -```python3 +```python class Solution: def sumOfLeftLeaves(self, root: TreeNode) -> int: if not root: @@ -246,7 +246,7 @@ class Solution: ``` **迭代** -```python3 +```python class Solution: def sumOfLeftLeaves(self, root: TreeNode) -> int: """ diff --git a/problems/0455.分发饼干.md b/problems/0455.分发饼干.md index 1711f638..210b492d 100644 --- a/problems/0455.分发饼干.md +++ b/problems/0455.分发饼干.md @@ -146,7 +146,7 @@ class Solution { ``` ### Python -```python3 +```python class Solution: # 思路1:优先考虑胃饼干 def findContentChildren(self, g: List[int], s: List[int]) -> int: diff --git a/problems/0463.岛屿的周长.md b/problems/0463.岛屿的周长.md index e19e06ee..9911dfe5 100644 --- a/problems/0463.岛屿的周长.md +++ b/problems/0463.岛屿的周长.md @@ -124,7 +124,7 @@ Python: ### 解法1: 扫描每个cell,如果当前位置为岛屿 grid[i][j] == 1, 从当前位置判断四边方向,如果边界或者是水域,证明有边界存在,res矩阵的对应cell加一。 -```python3 +```python class Solution: def islandPerimeter(self, grid: List[List[int]]) -> int: diff --git a/problems/0474.一和零.md b/problems/0474.一和零.md index 67e366f4..964df4a8 100644 --- a/problems/0474.一和零.md +++ b/problems/0474.一和零.md @@ -193,7 +193,7 @@ class Solution { ``` Python: -```python3 +```python class Solution: def findMaxForm(self, strs: List[str], m: int, n: int) -> int: dp = [[0] * (n + 1) for _ in range(m + 1)] # 默认初始化0 diff --git a/problems/0491.递增子序列.md b/problems/0491.递增子序列.md index 6d88119e..70b08d50 100644 --- a/problems/0491.递增子序列.md +++ b/problems/0491.递增子序列.md @@ -233,7 +233,7 @@ class Solution { python3 **回溯** -```python3 +```python class Solution: def __init__(self): self.paths = [] @@ -270,7 +270,7 @@ class Solution: self.path.pop() ``` **回溯+哈希表去重** -```python3 +```python class Solution: def __init__(self): self.paths = [] diff --git a/problems/0494.目标和.md b/problems/0494.目标和.md index f190b734..47d0784e 100644 --- a/problems/0494.目标和.md +++ b/problems/0494.目标和.md @@ -160,11 +160,16 @@ dp[j] 表示:填满j(包括j)这么大容积的包,有dp[j]种方法 那么只要搞到nums[i]的话,凑成dp[j]就有dp[j - nums[i]] 种方法。 -举一个例子,nums[i] = 2: dp[3],填满背包容量为3的话,有dp[3]种方法。 -那么只需要搞到一个2(nums[i]),有dp[3]方法可以凑齐容量为3的背包,相应的就有多少种方法可以凑齐容量为5的背包。 +例如:dp[j],j 为5, -那么需要把 这些方法累加起来就可以了,dp[j] += dp[j - nums[i]] +* 已经有一个1(nums[i]) 的话,有 dp[4]种方法 凑成 dp[5]。 +* 已经有一个2(nums[i]) 的话,有 dp[3]种方法 凑成 dp[5]。 +* 已经有一个3(nums[i]) 的话,有 dp[2]中方法 凑成 dp[5] +* 已经有一个4(nums[i]) 的话,有 dp[1]中方法 凑成 dp[5] +* 已经有一个5 (nums[i])的话,有 dp[0]中方法 凑成 dp[5] + +那么凑整dp[5]有多少方法呢,也就是把 所有的 dp[j - nums[i]] 累加起来。 所以求组合类问题的公式,都是类似这种: diff --git a/problems/0496.下一个更大元素I.md b/problems/0496.下一个更大元素I.md index f039c198..f9dfa308 100644 --- a/problems/0496.下一个更大元素I.md +++ b/problems/0496.下一个更大元素I.md @@ -222,8 +222,8 @@ class Solution { } } ``` -Python: -```python3 +Python3: +```python class Solution: def nextGreaterElement(self, nums1: List[int], nums2: List[int]) -> List[int]: result = [-1]*len(nums1) diff --git a/problems/0501.二叉搜索树中的众数.md b/problems/0501.二叉搜索树中的众数.md index 277f46f5..a2984ecc 100644 --- a/problems/0501.二叉搜索树中的众数.md +++ b/problems/0501.二叉搜索树中的众数.md @@ -470,7 +470,7 @@ class Solution { > 递归法 -```python3 +```python # Definition for a binary tree node. # class TreeNode: # def __init__(self, val=0, left=None, right=None): @@ -515,7 +515,7 @@ class Solution: > 迭代法-中序遍历-不使用额外空间,利用二叉搜索树特性 -```python3 +```python class Solution: def findMode(self, root: TreeNode) -> List[int]: stack = [] diff --git a/problems/0503.下一个更大元素II.md b/problems/0503.下一个更大元素II.md index c9532a22..36e183e1 100644 --- a/problems/0503.下一个更大元素II.md +++ b/problems/0503.下一个更大元素II.md @@ -124,7 +124,7 @@ class Solution { ``` Python: -```python3 +```python class Solution: def nextGreaterElements(self, nums: List[int]) -> List[int]: dp = [-1] * len(nums) diff --git a/problems/0518.零钱兑换II.md b/problems/0518.零钱兑换II.md index be60ac13..e72c5f85 100644 --- a/problems/0518.零钱兑换II.md +++ b/problems/0518.零钱兑换II.md @@ -207,7 +207,7 @@ class Solution { Python: -```python3 +```python class Solution: def change(self, amount: int, coins: List[int]) -> int: dp = [0]*(amount + 1) diff --git a/problems/0538.把二叉搜索树转换为累加树.md b/problems/0538.把二叉搜索树转换为累加树.md index 1d11d4ee..1b07b803 100644 --- a/problems/0538.把二叉搜索树转换为累加树.md +++ b/problems/0538.把二叉搜索树转换为累加树.md @@ -196,7 +196,7 @@ class Solution { ## Python **递归** -```python3 +```python # Definition for a binary tree node. # class TreeNode: # def __init__(self, val=0, left=None, right=None): diff --git a/problems/0669.修剪二叉搜索树.md b/problems/0669.修剪二叉搜索树.md index d17c0b1c..15f6a040 100644 --- a/problems/0669.修剪二叉搜索树.md +++ b/problems/0669.修剪二叉搜索树.md @@ -264,7 +264,7 @@ class Solution { ## Python **递归** -```python3 +```python # Definition for a binary tree node. # class TreeNode: # def __init__(self, val=0, left=None, right=None): diff --git a/problems/0841.钥匙和房间.md b/problems/0841.钥匙和房间.md index 8397690e..1cd13065 100644 --- a/problems/0841.钥匙和房间.md +++ b/problems/0841.钥匙和房间.md @@ -152,7 +152,6 @@ class Solution { -Python: python3 diff --git a/problems/1047.删除字符串中的所有相邻重复项.md b/problems/1047.删除字符串中的所有相邻重复项.md index 9a0bb1c1..b94e557d 100644 --- a/problems/1047.删除字符串中的所有相邻重复项.md +++ b/problems/1047.删除字符串中的所有相邻重复项.md @@ -194,7 +194,7 @@ class Solution { ``` Python: -```python3 +```python # 方法一,使用栈,推荐! class Solution: def removeDuplicates(self, s: str) -> str: @@ -207,7 +207,7 @@ class Solution: return "".join(res) # 字符串拼接 ``` -```python3 +```python # 方法二,使用双指针模拟栈,如果不让用栈可以作为备选方法。 class Solution: def removeDuplicates(self, s: str) -> str: diff --git a/problems/二叉树的递归遍历.md b/problems/二叉树的递归遍历.md index c481fd11..2fef68da 100644 --- a/problems/二叉树的递归遍历.md +++ b/problems/二叉树的递归遍历.md @@ -168,7 +168,7 @@ class Solution { ``` Python: -```python3 +```python # 前序遍历-递归-LC144_二叉树的前序遍历 class Solution: def preorderTraversal(self, root: TreeNode) -> List[int]: diff --git a/problems/周总结/20201003二叉树周末总结.md b/problems/周总结/20201003二叉树周末总结.md index a0b8c2dd..18bbf37f 100644 --- a/problems/周总结/20201003二叉树周末总结.md +++ b/problems/周总结/20201003二叉树周末总结.md @@ -34,8 +34,8 @@ public: // 此时就是:左右节点都不为空,且数值相同的情况 // 此时才做递归,做下一层的判断 - bool outside = compare(left->left, right->right); // 左子树:左、 右子树:左 (相对于求对称二叉树,只需改一下这里的顺序) - bool inside = compare(left->right, right->left); // 左子树:右、 右子树:右 + bool outside = compare(left->left, right->left); // 左子树:左、 右子树:左 (相对于求对称二叉树,只需改一下这里的顺序) + bool inside = compare(left->right, right->right); // 左子树:右、 右子树:右 bool isSame = outside && inside; // 左子树:中、 右子树:中 (逻辑处理) return isSame; diff --git a/problems/背包问题理论基础完全背包.md b/problems/背包问题理论基础完全背包.md index cea69c72..7abaf160 100644 --- a/problems/背包问题理论基础完全背包.md +++ b/problems/背包问题理论基础完全背包.md @@ -216,7 +216,7 @@ private static void testCompletePackAnotherWay(){ Python: -```python3 +```python # 先遍历物品,再遍历背包 def test_complete_pack1(): weight = [1, 3, 4] From 1ed3e9e8f4dff921e983e636f85f963a38839e05 Mon Sep 17 00:00:00 2001 From: youngyangyang04 <826123027@qq.com> Date: Tue, 1 Mar 2022 17:12:19 +0800 Subject: [PATCH 41/44] Update --- problems/二叉树总结篇.md | 2 +- problems/动态规划总结篇.md | 2 +- problems/回溯总结.md | 2 +- problems/贪心算法总结篇.md | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/problems/二叉树总结篇.md b/problems/二叉树总结篇.md index d1332e09..73faffa6 100644 --- a/problems/二叉树总结篇.md +++ b/problems/二叉树总结篇.md @@ -152,7 +152,7 @@ ![](https://code-thinking-1253855093.file.myqcloud.com/pics/20211030125421.png) -这个图是 [代码随想录知识星球](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ) 成员:[青](https://wx.zsxq.com/dweb2/index/footprint/185251215558842),所画,总结的非常好,分享给大家。 +这个图是 [代码随想录知识星球](https://programmercarl.com/other/kstar.html) 成员:[青](https://wx.zsxq.com/dweb2/index/footprint/185251215558842),所画,总结的非常好,分享给大家。 **最后,二叉树系列就这么完美结束了,估计这应该是最长的系列了,感谢大家33天的坚持与陪伴,接下来我们又要开始新的系列了「回溯算法」!** diff --git a/problems/动态规划总结篇.md b/problems/动态规划总结篇.md index 699d4435..cc973b23 100644 --- a/problems/动态规划总结篇.md +++ b/problems/动态规划总结篇.md @@ -118,7 +118,7 @@ ![](https://code-thinking-1253855093.file.myqcloud.com/pics/20211121223754.png) -这个图是 [代码随想录知识星球](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ) 成员:[青](https://wx.zsxq.com/dweb2/index/footprint/185251215558842),所画,总结的非常好,分享给大家。 +这个图是 [代码随想录知识星球](https://programmercarl.com/other/kstar.html) 成员:[青](https://wx.zsxq.com/dweb2/index/footprint/185251215558842),所画,总结的非常好,分享给大家。 这已经是全网对动规最深刻的讲解系列了。 diff --git a/problems/回溯总结.md b/problems/回溯总结.md index af171243..671e0a4e 100644 --- a/problems/回溯总结.md +++ b/problems/回溯总结.md @@ -432,7 +432,7 @@ N皇后问题分析: ![](https://code-thinking-1253855093.file.myqcloud.com/pics/20211030124742.png) -这个图是 [代码随想录知识星球](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ) 成员:[莫非毛](https://wx.zsxq.com/dweb2/index/footprint/828844212542),所画,总结的非常好,分享给大家。 +这个图是 [代码随想录知识星球](https://programmercarl.com/other/kstar.html) 成员:[莫非毛](https://wx.zsxq.com/dweb2/index/footprint/828844212542),所画,总结的非常好,分享给大家。 **回溯算法系列正式结束,新的系列终将开始,录友们准备开启新的征程!** diff --git a/problems/贪心算法总结篇.md b/problems/贪心算法总结篇.md index 6da43ea3..1db9b4dc 100644 --- a/problems/贪心算法总结篇.md +++ b/problems/贪心算法总结篇.md @@ -129,7 +129,7 @@ Carl个人认为:如果找出局部最优并可以推出全局最优,就是 ![](https://code-thinking-1253855093.file.myqcloud.com/pics/20211110121605.png) -这个图是 [代码随想录知识星球](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ) 成员:[青](https://wx.zsxq.com/dweb2/index/footprint/185251215558842)所画,总结的非常好,分享给大家。 +这个图是 [代码随想录知识星球](https://programmercarl.com/other/kstar.html) 成员:[青](https://wx.zsxq.com/dweb2/index/footprint/185251215558842)所画,总结的非常好,分享给大家。 很多没有接触过贪心的同学都会感觉贪心有啥可学的,但只要跟着「代码随想录」坚持下来之后,就会发现,贪心是一种很重要的算法思维而且并不简单,贪心往往妙的出其不意,触不及防! From ecde43b2fc292edbfaa1fec6b16d6941e879507f Mon Sep 17 00:00:00 2001 From: youngyangyang04 <826123027@qq.com> Date: Sat, 5 Mar 2022 17:12:34 +0800 Subject: [PATCH 42/44] update --- problems/0392.判断子序列.md | 2 +- problems/背包总结篇.md | 5 +++++ 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/problems/0392.判断子序列.md b/problems/0392.判断子序列.md index d64e1fd0..671576f7 100644 --- a/problems/0392.判断子序列.md +++ b/problems/0392.判断子序列.md @@ -77,7 +77,7 @@ if (s[i - 1] != t[j - 1]),此时相当于t要删除元素,t如果把当前 如果要是定义的dp[i][j]是以下标i为结尾的字符串s和以下标j为结尾的字符串t,初始化就比较麻烦了。 -这里dp[i][0]和dp[0][j]是没有含义的,仅仅是为了给递推公式做前期铺垫,所以初始化为0。 +dp[i][0] 表示以下标i-1为结尾的字符串,与空字符串的相同子序列长度,所以为0. dp[0][j]同理。 **其实这里只初始化dp[i][0]就够了,但一起初始化也方便,所以就一起操作了**,代码如下: diff --git a/problems/背包总结篇.md b/problems/背包总结篇.md index f80bcf29..a7852de3 100644 --- a/problems/背包总结篇.md +++ b/problems/背包总结篇.md @@ -82,6 +82,7 @@ ## 总结 + **这篇背包问题总结篇是对背包问题的高度概括,讲最关键的两部:递推公式和遍历顺序,结合力扣上的题目全都抽象出来了**。 **而且每一个点,我都给出了对应的力扣题目**。 @@ -90,7 +91,11 @@ 如果把我本篇总结出来的内容都掌握的话,可以说对背包问题理解的就很深刻了,用来对付面试中的背包问题绰绰有余! +背包问题总结: +![](https://code-thinking-1253855093.file.myqcloud.com/pics/背包问题1.jpeg) + +这个图是 [代码随想录知识星球](https://programmercarl.com/other/kstar.html) 成员:[海螺人](https://wx.zsxq.com/dweb2/index/footprint/844412858822412),所画结的非常好,分享给大家。 From f6360c701f5e1d251ad69e15c94c05273ff4235c Mon Sep 17 00:00:00 2001 From: youngyangyang04 <826123027@qq.com> Date: Sun, 6 Mar 2022 11:44:39 +0800 Subject: [PATCH 43/44] Update --- README.md | 5 ++--- .../前序/ACM模式如何构建二叉树.md | 16 +--------------- 2 files changed, 3 insertions(+), 18 deletions(-) diff --git a/README.md b/README.md index c1761f7b..0bf7fcdf 100644 --- a/README.md +++ b/README.md @@ -89,8 +89,7 @@ ## 前序 -* [「代码随想录」后序安排](https://mp.weixin.qq.com/s/4eeGJREy6E-v6D7cR_5A4g) -* [「代码随想录」学习社区](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ) +* [「代码随想录」学习社区](https://programmercarl.com/other/kstar.html) * 编程语言 @@ -124,7 +123,7 @@ * 算法性能分析 * [关于时间复杂度,你不知道的都在这里!](./problems/前序/关于时间复杂度,你不知道的都在这里!.md) - * [$O(n)$的算法居然超时了,此时的n究竟是多大?](./problems/前序/On的算法居然超时了,此时的n究竟是多大?.md) + * [O(n)的算法居然超时了,此时的n究竟是多大?](./problems/前序/On的算法居然超时了,此时的n究竟是多大?.md) * [通过一道面试题目,讲一讲递归算法的时间复杂度!](./problems/前序/通过一道面试题目,讲一讲递归算法的时间复杂度!.md) * [本周小结!(算法性能分析系列一)](./problems/周总结/20201210复杂度分析周末总结.md) * [关于空间复杂度,可能有几个疑问?](./problems/前序/关于空间复杂度,可能有几个疑问?.md) diff --git a/problems/前序/ACM模式如何构建二叉树.md b/problems/前序/ACM模式如何构建二叉树.md index fc7a1823..28c4b6f7 100644 --- a/problems/前序/ACM模式如何构建二叉树.md +++ b/problems/前序/ACM模式如何构建二叉树.md @@ -45,21 +45,7 @@ ![](https://code-thinking-1253855093.file.myqcloud.com/pics/20210914223147.png) -那么此时大家是不是应该知道了,数组如何转化成 二叉树了。**如果父节点的数组下标是i,那么它的左孩子下标就是i * 2 + 1,右孩子下标就是 i * 2 + 2**。计算过程为: - -如果父节点在第$k$层,第$m,m \in [0,2^k]$个节点,则其左孩子所在的位置必然为$k+1$层,第$2*(m-1)+1$个节点。 - -- 计算父节点在数组中的索引: - $$ - index_{father}=(\sum_{i=0}^{i=k-1}2^i)+m-1=2^k-1+m-1 - $$ - -- 计算左子节点在数组的索引: - $$ - index_{left}=(\sum_{i=0}^{i=k}2^i)+2*m-1-1=2^{k+1}+2m-3 - $$ - -- 故左孩子的下表为$index_{left}=index_{father}\times2+1$,同理可得到右子孩子的索引关系。也可以直接在左子孩子的基础上`+1`。 +那么此时大家是不是应该知道了,数组如何转化成 二叉树了。**如果父节点的数组下标是i,那么它的左孩子下标就是i * 2 + 1,右孩子下标就是 i * 2 + 2**。 那么这里又有同学疑惑了,这些我都懂了,但我还是不知道 应该 怎么构造。 From 5a848b76c184a447bdc96d8afe40071bbf7f9cd0 Mon Sep 17 00:00:00 2001 From: youngyangyang04 <826123027@qq.com> Date: Wed, 9 Mar 2022 11:22:51 +0800 Subject: [PATCH 44/44] Update --- problems/0127.单词接龙.md | 1 - problems/二叉树理论基础.md | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/problems/0127.单词接龙.md b/problems/0127.单词接龙.md index fb403a5b..407596c0 100644 --- a/problems/0127.单词接龙.md +++ b/problems/0127.单词接龙.md @@ -9,7 +9,6 @@ [力扣题目链接](https://leetcode-cn.com/problems/word-ladder/) - 字典 wordList 中从单词 beginWord 和 endWord 的 转换序列 是一个按下述规格形成的序列: * 序列中第一个单词是 beginWord 。 * 序列中最后一个单词是 endWord 。 diff --git a/problems/二叉树理论基础.md b/problems/二叉树理论基础.md index 62e3b19a..9c151e32 100644 --- a/problems/二叉树理论基础.md +++ b/problems/二叉树理论基础.md @@ -33,7 +33,7 @@ 什么是完全二叉树? -完全二叉树的定义如下:在完全二叉树中,除了最底层节点可能没填满外,其余每层节点数都达到最大值,并且最下面一层的节点都集中在该层最左边的若干位置。若最底层为第 h 层,则该层包含 1~ 2^h -1  个节点。 +完全二叉树的定义如下:在完全二叉树中,除了最底层节点可能没填满外,其余每层节点数都达到最大值,并且最下面一层的节点都集中在该层最左边的若干位置。若最底层为第 h 层,则该层包含 1~ 2^(h-1)  个节点。 **大家要自己看完全二叉树的定义,很多同学对完全二叉树其实不是真正的懂了。**