This commit is contained in:
krahets
2023-08-24 17:47:18 +08:00
parent 92a0853ab8
commit c6f0dfbdc8
10 changed files with 958 additions and 59 deletions

View File

@@ -2,11 +2,11 @@
comments: true
---
# 2.3   空间复杂度
# 2.4   空间复杂度
「空间复杂度 space complexity」用于衡量算法占用内存空间随着数据量变大时的增长趋势。这个概念与时间复杂度非常类似只需将“运行时间”替换为“占用内存空间”。
## 2.3.1   算法相关空间
## 2.4.1   算法相关空间
算法在运行过程中使用的内存空间主要包括以下几种。
@@ -26,7 +26,7 @@ comments: true
![算法使用的相关空间](space_complexity.assets/space_types.png)
<p align="center"> 图 2-9 &nbsp; 算法使用的相关空间 </p>
<p align="center"> 图 2-15 &nbsp; 算法使用的相关空间 </p>
=== "Java"
@@ -292,7 +292,7 @@ comments: true
```
## 2.3.2 &nbsp; 推算方法
## 2.4.2 &nbsp; 推算方法
空间复杂度的推算方法与时间复杂度大致相同,只需将统计对象从“操作数量”转为“使用空间大小”。
@@ -656,9 +656,9 @@ comments: true
```
## 2.3.3 &nbsp; 常见类型
## 2.4.3 &nbsp; 常见类型
设输入数据大小为 $n$ ,图 2-10 展示了常见的空间复杂度类型(从低到高排列)。
设输入数据大小为 $n$ ,图 2-16 展示了常见的空间复杂度类型(从低到高排列)。
$$
\begin{aligned}
@@ -669,7 +669,7 @@ $$
![常见的空间复杂度类型](space_complexity.assets/space_complexity_common_types.png)
<p align="center"> 图 2-10 &nbsp; 常见的空间复杂度类型 </p>
<p align="center"> 图 2-16 &nbsp; 常见的空间复杂度类型 </p>
!!! tip
@@ -1274,7 +1274,7 @@ $$
}
```
如图 2-11 所示,此函数的递归深度为 $n$ ,即同时存在 $n$ 个未返回的 `linear_recur()` 函数,使用 $O(n)$ 大小的栈帧空间:
如图 2-17 所示,此函数的递归深度为 $n$ ,即同时存在 $n$ 个未返回的 `linear_recur()` 函数,使用 $O(n)$ 大小的栈帧空间:
=== "Java"
@@ -1417,7 +1417,7 @@ $$
![递归函数产生的线性阶空间复杂度](space_complexity.assets/space_complexity_recursive_linear.png)
<p align="center"> 图 2-11 &nbsp; 递归函数产生的线性阶空间复杂度 </p>
<p align="center"> 图 2-17 &nbsp; 递归函数产生的线性阶空间复杂度 </p>
### 3. &nbsp; 平方阶 $O(n^2)$
@@ -1635,7 +1635,7 @@ $$
}
```
如图 2-12 所示,该函数的递归深度为 $n$ ,在每个递归函数中都初始化了一个数组,长度分别为 $n, n-1, n-2, ..., 2, 1$ ,平均长度为 $n / 2$ ,因此总体占用 $O(n^2)$ 空间:
如图 2-18 所示,该函数的递归深度为 $n$ ,在每个递归函数中都初始化了一个数组,长度分别为 $n, n-1, n-2, ..., 2, 1$ ,平均长度为 $n / 2$ ,因此总体占用 $O(n^2)$ 空间:
=== "Java"
@@ -1796,11 +1796,11 @@ $$
![递归函数产生的平方阶空间复杂度](space_complexity.assets/space_complexity_recursive_quadratic.png)
<p align="center"> 图 2-12 &nbsp; 递归函数产生的平方阶空间复杂度 </p>
<p align="center"> 图 2-18 &nbsp; 递归函数产生的平方阶空间复杂度 </p>
### 4. &nbsp; 指数阶 $O(2^n)$
指数阶常见于二叉树。观察图 2-13 ,高度为 $n$ 的“满二叉树”的节点数量为 $2^n - 1$ ,占用 $O(2^n)$ 空间:
指数阶常见于二叉树。观察图 2-19 ,高度为 $n$ 的“满二叉树”的节点数量为 $2^n - 1$ ,占用 $O(2^n)$ 空间:
=== "Java"
@@ -1968,7 +1968,7 @@ $$
![满二叉树产生的指数阶空间复杂度](space_complexity.assets/space_complexity_exponential.png)
<p align="center"> 图 2-13 &nbsp; 满二叉树产生的指数阶空间复杂度 </p>
<p align="center"> 图 2-19 &nbsp; 满二叉树产生的指数阶空间复杂度 </p>
### 5. &nbsp; 对数阶 $O(\log n)$
@@ -1976,7 +1976,7 @@ $$
再例如将数字转化为字符串,输入一个正整数 $n$ ,它的位数为 $\log_{10} n + 1$ ,即对应字符串长度为 $\log_{10} n + 1$ ,因此空间复杂度为 $O(\log_{10} n + 1) = O(\log n)$ 。
## 2.3.4 &nbsp; 权衡时间与空间
## 2.4.4 &nbsp; 权衡时间与空间
理想情况下,我们希望算法的时间复杂度和空间复杂度都能达到最优。然而在实际情况中,同时优化时间复杂度和空间复杂度通常是非常困难的。