Skip to content

Commit 7455e90

Browse files
Merge pull request SharingSource#68 from SharingSource/ac_oier
✨feat: Add 863
2 parents 55b78f6 + 81cc151 commit 7455e90

File tree

5 files changed

+305
-0
lines changed

5 files changed

+305
-0
lines changed

Index/二叉树.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
| ------------------------------------------------------------ | ------------------------------------------------------------ | ---- | -------- |
33
| [297. 二叉树的序列化与反序列化](https://leetcode-cn.com/problems/serialize-and-deserialize-binary-tree/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/xu-lie-hua-er-cha-shu-lcof/solution/gong-shui-san-xie-er-cha-shu-de-xu-lie-h-n89a/) | 困难 | 🤩🤩🤩🤩🤩 |
44
| [783. 二叉搜索树节点最小距离](https://leetcode-cn.com/problems/minimum-distance-between-bst-nodes/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/minimum-distance-between-bst-nodes/solution/gong-shui-san-xie-yi-ti-san-jie-shu-de-s-7r17/) | 简单 | 🤩🤩🤩 |
5+
| [863. 二叉树中所有距离为 K 的结点](https://leetcode-cn.com/problems/all-nodes-distance-k-in-binary-tree/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/all-nodes-distance-k-in-binary-tree/solution/gong-shui-san-xie-yi-ti-shuang-jie-jian-x6hak/) | 中等 | 🤩🤩🤩🤩 |
56
| [938. 二叉搜索树的范围和](https://leetcode-cn.com/problems/range-sum-of-bst/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/range-sum-of-bst/solution/gong-shui-san-xie-yi-ti-shuang-jie-di-gu-q2fo/) | 简单 | 🤩🤩🤩 |
67
| [993. 二叉树的堂兄弟节点](https://leetcode-cn.com/problems/cousins-in-binary-tree/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/cousins-in-binary-tree/solution/gong-shui-san-xie-shu-de-sou-suo-dfs-bfs-b200/) | 简单 | 🤩🤩 |
78
| [剑指 Offer 37. 序列化二叉树](https://leetcode-cn.com/problems/xu-lie-hua-er-cha-shu-lcof/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/xu-lie-hua-er-cha-shu-lcof/solution/gong-shui-san-xie-er-cha-shu-de-xu-lie-h-n89a/) | 困难 | 🤩🤩🤩🤩🤩 |

Index/图论 BFS.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
| [752. 打开转盘锁](https://leetcode-cn.com/problems/open-the-lock/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/open-the-lock/solution/gong-shui-san-xie-yi-ti-shuang-jie-shuan-wyr9/) | 中等 | 🤩🤩🤩🤩 |
66
| [773. 滑动谜题](https://leetcode-cn.com/problems/sliding-puzzle/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/sliding-puzzle/solution/gong-shui-san-xie-fa-hui-a-suan-fa-zui-d-3go8/) | 困难 | 🤩🤩🤩🤩 |
77
| [815. 公交路线](https://leetcode-cn.com/problems/bus-routes/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/bus-routes/solution/gong-shui-san-xie-yi-ti-shuang-jie-po-su-1roh/) | 困难 | 🤩🤩🤩🤩 |
8+
| [863. 二叉树中所有距离为 K 的结点](https://leetcode-cn.com/problems/all-nodes-distance-k-in-binary-tree/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/all-nodes-distance-k-in-binary-tree/solution/gong-shui-san-xie-yi-ti-shuang-jie-jian-x6hak/) | 中等 | 🤩🤩🤩🤩 |
89
| [909. 蛇梯棋](https://leetcode-cn.com/problems/snakes-and-ladders/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/snakes-and-ladders/solution/gong-shui-san-xie-bfs-mo-ni-by-ac_oier-woh6/) | 中等 | 🤩🤩🤩🤩 |
910
| [1162. 地图分析](https://leetcode-cn.com/problems/as-far-from-land-as-possible/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/as-far-from-land-as-possible/solution/gong-shui-san-xie-ru-he-shi-yong-duo-yua-vlea/) | 中等 | 🤩🤩🤩🤩 |
1011
| [LCP 07. 传递信息](https://leetcode-cn.com/problems/chuan-di-xin-xi/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/chuan-di-xin-xi/solution/gong-shui-san-xie-tu-lun-sou-suo-yu-dong-cyxo/) | 简单 | 🤩🤩🤩🤩 |

Index/图论 DFS.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
| ------------------------------------------------------------ | ------------------------------------------------------------ | ---- | -------- |
33
| [403. 青蛙过河](https://leetcode-cn.com/problems/frog-jump/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/frog-jump/solution/gong-shui-san-xie-yi-ti-duo-jie-jiang-di-74fw/) | 困难 | 🤩🤩🤩🤩 |
44
| [778. 水位上升的泳池中游泳](https://leetcode-cn.com/problems/swim-in-rising-water/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/swim-in-rising-water/solution/gong-shui-san-xie-yi-ti-shuang-jie-krusk-7c6o/) | 困难 | 🤩🤩🤩 |
5+
| [863. 二叉树中所有距离为 K 的结点](https://leetcode-cn.com/problems/all-nodes-distance-k-in-binary-tree/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/all-nodes-distance-k-in-binary-tree/solution/gong-shui-san-xie-yi-ti-shuang-jie-jian-x6hak/) | 中等 | 🤩🤩🤩🤩 |
56
| [1723. 完成所有工作的最短时间](https://leetcode-cn.com/problems/find-minimum-time-to-finish-all-jobs/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/find-minimum-time-to-finish-all-jobs/solution/gong-shui-san-xie-yi-ti-shuang-jie-jian-4epdd/) | 困难 | 🤩🤩🤩 |
67
| [1766. 互质树](https://leetcode-cn.com/problems/tree-of-coprimes/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/tree-of-coprimes/solution/bu-tai-yi-yang-de-dfs-ji-lu-suo-you-zui-d3xeu/) | 困难 | 🤩🤩🤩🤩 |
78
| [LCP 07. 传递信息](https://leetcode-cn.com/problems/chuan-di-xin-xi/) | [LeetCode 题解链接](https://leetcode-cn.com/problems/chuan-di-xin-xi/solution/gong-shui-san-xie-tu-lun-sou-suo-yu-dong-cyxo/) | 简单 | 🤩🤩🤩🤩 |
Lines changed: 110 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,110 @@
1+
### 题目描述
2+
3+
这是 LeetCode 上的 **[1834. 单线程 CPU]()** ,难度为 **中等**
4+
5+
Tag : 「模拟」、「排序」、「优先队列」
6+
7+
8+
9+
给你一个二维数组 $tasks$,用于表示 $n$ 项从 $0$ 到 $n - 1$ 编号的任务。
10+
11+
其中 $tasks[i] = [enqueueTime_i, processingTime_i]$ 意味着第 $i$ 项任务将会于 $enqueueTime_i$ 时进入任务队列,需要 $processingTime_i$ 的时长完成执行。
12+
13+
现有一个单线程 CPU ,同一时间只能执行**最多一项**任务,该 CPU 将会按照下述方式运行:
14+
* 如果 CPU 空闲,且任务队列中没有需要执行的任务,则 CPU 保持空闲状态。
15+
* 如果 CPU 空闲,但任务队列中有需要执行的任务,则 CPU 将会选择 执行时间最短 的任务开始执行。如果多个任务具有同样的最短执行时间,则选择下标最小的任务开始执行。
16+
* 一旦某项任务开始执行,CPU 在 执行完整个任务 前都不会停止。
17+
* CPU 可以在完成一项任务后,立即开始执行一项新任务。
18+
19+
返回 CPU 处理任务的顺序。
20+
21+
示例 1:
22+
23+
```
24+
输入:tasks = [[1,2],[2,4],[3,2],[4,1]]
25+
26+
输出:[0,2,3,1]
27+
28+
解释:事件按下述流程运行:
29+
- time = 1 ,任务 0 进入任务队列,可执行任务项 = {0}
30+
- 同样在 time = 1 ,空闲状态的 CPU 开始执行任务 0 ,可执行任务项 = {}
31+
- time = 2 ,任务 1 进入任务队列,可执行任务项 = {1}
32+
- time = 3 ,任务 2 进入任务队列,可执行任务项 = {1, 2}
33+
- 同样在 time = 3 ,CPU 完成任务 0 并开始执行队列中用时最短的任务 2 ,可执行任务项 = {1}
34+
- time = 4 ,任务 3 进入任务队列,可执行任务项 = {1, 3}
35+
- time = 5 ,CPU 完成任务 2 并开始执行队列中用时最短的任务 3 ,可执行任务项 = {1}
36+
- time = 6 ,CPU 完成任务 3 并开始执行任务 1 ,可执行任务项 = {}
37+
- time = 10 ,CPU 完成任务 1 并进入空闲状态
38+
```
39+
示例 2:
40+
```
41+
输入:tasks = [[7,10],[7,12],[7,5],[7,4],[7,2]]
42+
43+
输出:[4,3,2,0,1]
44+
45+
解释:事件按下述流程运行:
46+
- time = 7 ,所有任务同时进入任务队列,可执行任务项 = {0,1,2,3,4}
47+
- 同样在 time = 7 ,空闲状态的 CPU 开始执行任务 4 ,可执行任务项 = {0,1,2,3}
48+
- time = 9 ,CPU 完成任务 4 并开始执行任务 3 ,可执行任务项 = {0,1,2}
49+
- time = 13 ,CPU 完成任务 3 并开始执行任务 2 ,可执行任务项 = {0,1}
50+
- time = 18 ,CPU 完成任务 2 并开始执行任务 0 ,可执行任务项 = {1}
51+
- time = 28 ,CPU 完成任务 0 并开始执行任务 1 ,可执行任务项 = {}
52+
- time = 40 ,CPU 完成任务 1 并进入空闲状态
53+
```
54+
55+
提示:
56+
* tasks.length == n
57+
* 1 <= n <= $10^5$
58+
* 1 <= $enqueueTime_i$, $processingTime_i$ <= $10^9$
59+
60+
---
61+
62+
### 模拟 + 数据结构
63+
64+
65+
66+
代码:
67+
```Java
68+
class Solution {
69+
public int[] getOrder(int[][] ts) {
70+
int n = ts.length;
71+
int[][] nts = new int[n][3];
72+
for (int i = 0; i < n; i++) nts[i] = new int[]{ts[i][0], ts[i][1], i};
73+
Arrays.sort(nts, (a,b)->a[0]-b[0]);
74+
PriorityQueue<int[]> q = new PriorityQueue<>((a,b)->{
75+
if (a[1] != b[1]) return a[1] - b[1];
76+
return a[2] - b[2];
77+
});
78+
int[] ans = new int[n];
79+
for (int time = 1, j = 0, idx = 0; idx < n; ) {
80+
// 如果当前任务可以添加到「队列」中(满足入队时间)则进行入队
81+
while (j < n && nts[j][0] <= time) q.add(nts[j++]);
82+
if (q.isEmpty()) {
83+
// 如果当前「队列」没有任务,直接跳到下个任务的入队时间
84+
time = nts[j][0];
85+
} else {
86+
// 如果有可执行任务的话,根据优先级将任务出队(记录下标),并跳到该任务完成时间点
87+
int[] cur = q.poll();
88+
ans[idx++] = cur[2];
89+
time += cur[1];
90+
}
91+
}
92+
return ans;
93+
}
94+
}
95+
```
96+
* 时间复杂度:
97+
* 空间复杂度:
98+
99+
---
100+
101+
### 最后
102+
103+
这是我们「刷穿 LeetCode」系列文章的第 `No.1834` 篇,系列开始于 2021/01/01,截止于起始日 LeetCode 上共有 1916 道题目,部分是有锁题,我们将先把所有不带锁的题目刷完。
104+
105+
在这个系列文章里面,除了讲解解题思路以外,还会尽可能给出最为简洁的代码。如果涉及通解还会相应的代码模板。
106+
107+
为了方便各位同学能够电脑上进行调试和提交代码,我建立了相关的仓库:https://github.com/SharingSource/LogicStack-LeetCode
108+
109+
在仓库地址里,你可以看到系列文章的题解链接、系列文章的相应代码、LeetCode 原题链接和其他优选题解。
110+
Lines changed: 192 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,192 @@
1+
### 题目描述
2+
3+
这是 LeetCode 上的 **[863. 二叉树中所有距离为 K 的结点](https://leetcode-cn.com/problems/all-nodes-distance-k-in-binary-tree/solution/gong-shui-san-xie-yi-ti-shuang-jie-jian-x6hak/)** ,难度为 **中等**
4+
5+
Tag : 「图论 BFS」、「图论 DFS」、「二叉树」
6+
7+
8+
9+
给定一个二叉树(具有根结点 root), 一个目标结点 target ,和一个整数值 K 。
10+
11+
返回到目标结点 target 距离为 K 的所有结点的值的列表。 答案可以以任何顺序返回。
12+
13+
14+
示例 1:
15+
```
16+
输入:root = [3,5,1,6,2,0,8,null,null,7,4], target = 5, K = 2
17+
18+
输出:[7,4,1]
19+
20+
解释:
21+
所求结点为与目标结点(值为 5)距离为 2 的结点,
22+
值分别为 7,4,以及 1
23+
```
24+
![](https://s3-lc-upload.s3.amazonaws.com/uploads/2018/06/28/sketch0.png)
25+
26+
注意,输入的 "root" 和 "target" 实际上是树上的结点。
27+
上面的输入仅仅是对这些对象进行了序列化描述。
28+
29+
提示:
30+
* 给定的树是非空的。
31+
* 树上的每个结点都具有唯一的值 0 <= node.val <= 500 。
32+
* 目标结点 target 是树上的结点。
33+
* 0 <= K <= 1000.
34+
35+
---
36+
37+
### 基本分析
38+
39+
显然,如果题目是以图的形式给出的话,我们可以很容易通过「`BFS` / 迭代加深」找到距离为 $k$ 的节点集。
40+
41+
而树是一类特殊的图,我们可以通过将二叉树转换为图的形式,再进行「`BFS` / 迭代加深」。
42+
43+
由于二叉树每个点最多有 $2$ 个子节点,点和边的数量接近,属于稀疏图,因此我们可以使用「邻接表」的形式进行存储。
44+
45+
建图方式为:对于二叉树中相互连通的节点(`root``root.left``root``root.right`),建立一条无向边。
46+
47+
建图需要遍历整棵树,使用 `DFS` 或者 `BFS` 均可。
48+
49+
由于所有边的权重均为 $1$,我们可以使用 「`BFS` / 迭代加深」 找到从目标节点 `target` 出发,与目标节点距离为 $k$ 的节点,然后将其添加到答案中。
50+
51+
>一些细节:利用每个节点具有唯一的值,我们可以直接使用节点值进行建图和搜索。
52+
53+
54+
---
55+
56+
### 建图 + `BFS`
57+
58+
由「基本分析」,可写出「建图 + `BFS`」的实现。
59+
60+
![image.png](https://pic.leetcode-cn.com/1627435303-JWROoB-image.png)
61+
62+
代码:
63+
```Java []
64+
class Solution {
65+
int N = 1010, M = N * 2;
66+
int[] he = new int[N], e = new int[M], ne = new int[M];
67+
int idx;
68+
void add(int a, int b) {
69+
e[idx] = b;
70+
ne[idx] = he[a];
71+
he[a] = idx++;
72+
}
73+
boolean[] vis = new boolean[N];
74+
public List<Integer> distanceK(TreeNode root, TreeNode t, int k) {
75+
List<Integer> ans = new ArrayList<>();
76+
Arrays.fill(he, -1);
77+
dfs(root);
78+
Deque<Integer> d = new ArrayDeque<>();
79+
d.addLast(t.val);
80+
vis[t.val] = true;
81+
while (!d.isEmpty() && k >= 0) {
82+
int size = d.size();
83+
while (size-- > 0) {
84+
int poll = d.pollFirst();
85+
if (k == 0) {
86+
ans.add(poll);
87+
continue;
88+
}
89+
for (int i = he[poll]; i != -1 ; i = ne[i]) {
90+
int j = e[i];
91+
if (!vis[j]) {
92+
d.addLast(j);
93+
vis[j] = true;
94+
}
95+
}
96+
}
97+
k--;
98+
}
99+
return ans;
100+
}
101+
void dfs(TreeNode root) {
102+
if (root == null) return;
103+
if (root.left != null) {
104+
add(root.val, root.left.val);
105+
add(root.left.val, root.val);
106+
dfs(root.left);
107+
}
108+
if (root.right != null) {
109+
add(root.val, root.right.val);
110+
add(root.right.val, root.val);
111+
dfs(root.right);
112+
}
113+
}
114+
}
115+
```
116+
* 时间复杂度:通过 `DFS` 进行建图的复杂度为 $O(n)$;通过 `BFS` 找到距离 $target$ 为 $k$ 的节点,复杂度为 $O(n)$。整体复杂度为 $O(n)$
117+
* 空间复杂度:$O(n)$
118+
119+
---
120+
121+
### 建图 + 迭代加深
122+
123+
由「基本分析」,可写出「建图 + 迭代加深」的实现。
124+
125+
迭代加深的形式,我们只需要结合题意,搜索深度为 $k$ 的这一层即可。
126+
127+
![image.png](https://pic.leetcode-cn.com/1627435278-iGCsTQ-image.png)
128+
129+
代码:
130+
```Java
131+
class Solution {
132+
int N = 1010, M = N * 2;
133+
int[] he = new int[N], e = new int[M], ne = new int[M];
134+
int idx;
135+
void add(int a, int b) {
136+
e[idx] = b;
137+
ne[idx] = he[a];
138+
he[a] = idx++;
139+
}
140+
boolean[] vis = new boolean[N];
141+
public List<Integer> distanceK(TreeNode root, TreeNode t, int k) {
142+
List<Integer> ans = new ArrayList<>();
143+
Arrays.fill(he, -1);
144+
dfs(root);
145+
vis[t.val] = true;
146+
find(t.val, k, 0, ans);
147+
return ans;
148+
}
149+
void find(int root, int max, int cur, List<Integer> ans) {
150+
if (cur == max) {
151+
ans.add(root);
152+
return ;
153+
}
154+
for (int i = he[root]; i != -1; i = ne[i]) {
155+
int j = e[i];
156+
if (!vis[j]) {
157+
vis[j] = true;
158+
find(j, max, cur + 1, ans);
159+
}
160+
}
161+
}
162+
void dfs(TreeNode root) {
163+
if (root == null) return;
164+
if (root.left != null) {
165+
add(root.val, root.left.val);
166+
add(root.left.val, root.val);
167+
dfs(root.left);
168+
}
169+
if (root.right != null) {
170+
add(root.val, root.right.val);
171+
add(root.right.val, root.val);
172+
dfs(root.right);
173+
}
174+
}
175+
}
176+
```
177+
* 时间复杂度:通过 `DFS` 进行建图的复杂度为 $O(n)$;通过迭代加深找到距离 $target$ 为 $k$ 的节点,复杂度为 $O(n)$。整体复杂度为 $O(n)$
178+
* 空间复杂度:$O(n)$
179+
180+
181+
---
182+
183+
### 最后
184+
185+
这是我们「刷穿 LeetCode」系列文章的第 `No.863` 篇,系列开始于 2021/01/01,截止于起始日 LeetCode 上共有 1916 道题目,部分是有锁题,我们将先将所有不带锁的题目刷完。
186+
187+
在这个系列文章里面,除了讲解解题思路以外,还会尽可能给出最为简洁的代码。如果涉及通解还会相应的代码模板。
188+
189+
为了方便各位同学能够电脑上进行调试和提交代码,我建立了相关的仓库:https://github.com/SharingSource/LogicStack-LeetCode
190+
191+
在仓库地址里,你可以看到系列文章的题解链接、系列文章的相应代码、LeetCode 原题链接和其他优选题解。
192+

0 commit comments

Comments
 (0)