Mention figures and tables in normal texts.

Fix some figures.
Finetune texts.
This commit is contained in:
krahets
2023-08-21 19:33:45 +08:00
parent 1aff6d6cc2
commit 106f02809a
64 changed files with 277 additions and 240 deletions

View File

@@ -8,7 +8,7 @@
给定一个二叉树,搜索并记录所有值为 $7$ 的节点,请返回节点列表。
对于此题,我们前序遍历这颗树,并判断当前节点的值是否为 $7$ ,若是则将该节点的值加入到结果列表 `res` 之中。
对于此题,我们前序遍历这颗树,并判断当前节点的值是否为 $7$ ,若是则将该节点的值加入到结果列表 `res` 之中。相关过程实现如下图和以下代码所示。
=== "Java"
@@ -172,7 +172,7 @@
在每次“尝试”中,我们通过将当前节点添加进 `path` 来记录路径;而在“回退”前,我们需要将该节点从 `path` 中弹出,**以恢复本次尝试之前的状态**。
观察过程,**我们可以将尝试和回退理解为“前进”与“撤销”**,两个操作是互为逆向的。
观察下图所示的过程,**我们可以将尝试和回退理解为“前进”与“撤销”**,两个操作是互为逆向的。
=== "<1>"
![尝试与回退](backtracking_algorithm.assets/preorder_find_paths_step1.png)
@@ -289,7 +289,7 @@
[class]{}-[func]{pre_order}
```
剪枝是一个非常形象的名词。在搜索过程中,**我们“剪掉”了不满足约束条件的搜索分支**,避免许多无意义的尝试,从而实现搜索效率的提高
剪枝是一个非常形象的名词。如下图所示,在搜索过程中,**我们“剪掉”了不满足约束条件的搜索分支**,避免许多无意义的尝试,从而提高了搜索效率。
![根据约束条件剪枝](backtracking_algorithm.assets/preorder_find_constrained_paths.png)
@@ -761,7 +761,7 @@
[class]{}-[func]{backtrack}
```
根据题意,找到值为 7 的节点后应该继续搜索,**因此我们需要将记录解之后的 `return` 语句删除**。下图对比了保留或删除 `return` 语句的搜索过程。
根据题意,我们在找到值为 7 的节点后应该继续搜索,**因此需要将记录解之后的 `return` 语句删除**。下图对比了保留或删除 `return` 语句的搜索过程。
![保留与删除 return 的搜索过程对比](backtracking_algorithm.assets/backtrack_remove_return_or_not.png)

View File

@@ -8,7 +8,7 @@
![4 皇后问题的解](n_queens_problem.assets/solution_4_queens.png)
本题共包含三个约束条件:**多个皇后不能在同一行、同一列、同一对角线**。值得注意的是,对角线分为主对角线 `\` 和次对角线 `/` 两种。
下图展示了本题的三个约束条件:**多个皇后不能在同一行、同一列、同一对角线**。值得注意的是,对角线分为主对角线 `\` 和次对角线 `/` 两种。
![n 皇后问题的约束条件](n_queens_problem.assets/n_queens_constraints.png)
@@ -30,9 +30,9 @@
那么,如何处理对角线约束呢?设棋盘中某个格子的行列索引为 $(row, col)$ ,选定矩阵中的某条主对角线,我们发现该对角线上所有格子的行索引减列索引都相等,**即对角线上所有格子的 $row - col$ 为恒定值**。
也就是说,如果两个格子满足 $row_1 - col_1 = row_2 - col_2$ ,则它们一定处在同一条主对角线上。利用该规律,我们可以借助一个数组 `diag1` 记录每条主对角线上是否有皇后。
也就是说,如果两个格子满足 $row_1 - col_1 = row_2 - col_2$ ,则它们一定处在同一条主对角线上。利用该规律,我们可以借助下图所示的数组 `diag1` 记录每条主对角线上是否有皇后。
同理,**次对角线上的所有格子的 $row + col$ 是恒定值**。我们可以使用相同方法,借助数组 `diag2` 来处理次对角线约束。
同理,**次对角线上的所有格子的 $row + col$ 是恒定值**。我们同样也可以借助数组 `diag2` 来处理次对角线约束。
![处理列约束和对角线约束](n_queens_problem.assets/n_queens_cols_diagonals.png)

View File

@@ -155,9 +155,9 @@
### 相等元素剪枝
观察发现,在第一轮中,选择 $1$ 或选择 $\hat{1}$ 是等价的,在这两个选择之下生成的所有排列都是重复的。因此应该把 $\hat{1}$ 剪枝掉。
观察下图,在第一轮中,选择 $1$ 或选择 $\hat{1}$ 是等价的,在这两个选择之下生成的所有排列都是重复的。因此应该把 $\hat{1}$ 剪枝掉。
同理,在第一轮选择 $2$ 后,第二轮选择中的 $1$ 和 $\hat{1}$ 也会产生重复分支,因此也应将第二轮的 $\hat{1}$ 剪枝。
同理,在第一轮选择 $2$ 后,第二轮选择中的 $1$ 和 $\hat{1}$ 也会产生重复分支,因此也应将第二轮的 $\hat{1}$ 剪枝。
本质上看,**我们的目标是在某一轮选择中,保证多个相等的元素仅被选择一次**。

View File

@@ -131,11 +131,11 @@
1. 第一轮和第二轮分别选择 $3$ , $4$ ,会生成包含这两个元素的所有子集,记为 $[3, 4, \dots]$ 。
2. 若第一轮选择 $4$ **则第二轮应该跳过 $3$** ,因为该选择产生的子集 $[4, 3, \dots]$ 和 `1.` 中生成的子集完全重复。
分支越靠右,需要排除的分支也越多,例如:
如下图所示,每一层的选择都是从左到右被逐个尝试的,因此越靠右剪枝越多。
1. 前两轮选择 $3$ , $5$ ,生成子集 $[3, 5, \dots]$ 。
2. 前两轮选择 $4$ , $5$ ,生成子集 $[4, 5, \dots]$ 。
3. 若第一轮选择 $5$ **则第二轮应该跳过 $3$ 和 $4$** ,因为子集 $[5, 3, \dots]$ 和子集 $[5, 4, \dots]$ 和 `1.` , `2.` 中生成的子集完全重复。
3. 若第一轮选择 $5$ **则第二轮应该跳过 $3$ 和 $4$** ,因为子集 $[5, 3, \dots]$ 和子集 $[5, 4, \dots]$ 和 `1.` , `2.` 中描述的子集完全重复。
![不同选择顺序导致的重复子集](subset_sum_problem.assets/subset_sum_i_pruning.png)
@@ -258,7 +258,7 @@
相比于上题,**本题的输入数组可能包含重复元素**,这引入了新的问题。例如,给定数组 $[4, \hat{4}, 5]$ 和目标元素 $9$ ,则现有代码的输出结果为 $[4, 5], [\hat{4}, 5]$ ,出现了重复子集。
**造成这种重复的原因是相等元素在某轮中被多次选择**。下图所示,第一轮共有三个选择,其中两个都为 $4$ ,会产生两个重复的搜索分支,从而输出重复子集;同理,第二轮的两个 $4$ 也会产生重复子集。
**造成这种重复的原因是相等元素在某轮中被多次选择**。下图,第一轮共有三个选择,其中两个都为 $4$ ,会产生两个重复的搜索分支,从而输出重复子集;同理,第二轮的两个 $4$ 也会产生重复子集。
![相等元素导致的重复子集](subset_sum_problem.assets/subset_sum_ii_repeat.png)