3-1特殊矩阵的压缩存储
看完栈、队列,看特殊矩阵的压缩存储
【注意】数组中元素的下标是从 0开始的。
3.4_特殊矩阵的压缩存储_哔哩哔哩_bilibili
1.数组的存储结构
1.1一维数组
一维数组 A[0...n-1],格数组元素大小相同,在物理上连续存放。其存储结构关系式为:
其中,LOC是起始地址。数组下标默认从 0 开始。
1.2.二维数组
二维数组在逻辑上是一个二维列表。在内存上,对于多维数组,有两种映射方法:按行优先存储、按列优先存储。

把非线性的二维数组拉成了一个线性存储的存储结构,那么它的好处就是可以实现像一维数组一样的随机存储,即只需要用LOC加上目标元素的位置。
1.2.1行优先存储
设二维数组 b[M][N],若按照行优先存储结构,先存储行号较小的元素,行号相等先存储列号较小的元素:
如果给出的是下标范围为 [0,n],那么其实是有 n+1 个元素,即:
1.2.2列优先存储
按列优先方式存储时,得出存储结构关系式为:
2.特殊矩阵
压缩存储:指为多个值相同的元素只分配一个存储空间,对零元素不分配存储空间。其目的是节省存储空间。
特殊矩阵:指具有许多相同矩阵元素或零元素,并且这些相同矩阵元素或零元素的分布有一定规律性的矩阵。常见的特殊矩阵有对称矩阵、上(下)三角矩阵、对角矩阵等。
特殊矩阵的压缩存储方法:找出特殊矩阵中值相同的矩阵元素的分布规律,把那些呈现规律性分布的、值相同的多个矩阵元素压缩存储到一个存储空间中。
2.1对称矩阵
方阵
若n阶方阵中任意一个元素 都有 = 则该矩阵为对称矩阵。
因为两个三角对称相等,所以只需要存储一半三角。

例如将下三角放入一维数组:

可以使用行优先的原则,把每行元素存入一维数组中。
- 那么这个一维数组它的大小就是 1+2+3+...+n 为。
那么在一维数组中,就有:0 ~ 个数。
- 对称矩阵压缩之后,可以实现一个“映射”函数,矩阵下标 → 一维数组下标。
例如按行优先,通过上面的一维数组存储结构:
, 是第 个元素(前面几行的元素+j 所在那一行前面的几个),那么,前面就是有 行元素了。
如果是上三角矩阵,但是由于对阵矩阵 = 的性质,所有可以转换成下三角矩阵。那么总映射为:
2.2三角矩阵

分为上三角矩阵、下三角矩阵。
2.2.1下三角矩阵

和对称矩阵同样,那么在一维数组中,就有:0 ~ 个数,但是多在后面 的位置存储C。

(i≥j) → B[k]
从下标 1 开始:
2.2.2上三角矩阵
(i≤j) → B[k]
从下标 1 开始:
例1、若将 n 阶上三角矩阵 A 按列优先级压缩存放在一维数组 B[1...n(n+1)/2+1] 中, 则存放到B[k] 中的非零元素 (1 ≤ i, j ≤ n) 的下标 i, j 与 k 的对应关系是( C )。 A. i ( i + 1 ) / 2 + j B. i ( i - 1 ) / 2 + j - 1 C. j ( j - 1 ) / 2 + i D. j ( j - 1 ) / 2 + i - 1
解:按列优先存储,故元素 前面有 j - 1 列,
共有 1 + 2 + 3 + ... +j -1 = j ( j - 1 ) / 2 个元素,元素 在第 j 列上是第 i 个元素,
数组 B 的下标是从 1 开始,因此 k = j ( j - 1 ) / 2 + i。
例2、若将 n 阶下三角矩阵 A 按列优先顺序压缩存放在一维数组 B[1...n(n+1)/2+1] 中,则存放到 B[k] 中的非零元素 (1 ≤ i, j ≤ n) 的下标 i, j 与 k 的对应关系是( B )。 A. (j - 1) (2n - j + 1) / 2 + i - j B. (j - 1) (2n - j + 2) / 2 + i - j + 1 C. (j - 1) (2n - j + 2) / 2 + i - j D. (j - 1) (2n - j + 1) / 2 + i - j + 1
解:按列优先存储,故元素 之前有 j - 1 列,
共有 n + (n - 1) + ... + (n - j + 2) = (j-1)(2n - j + 2) / 2 个元素,
元素 是第 j 列上第 i - j + 1 个元素,
数组 B 下标从 1 开始,k = (j - 1) (2n - j + 2) / 2 + i - j + 1。
例3、【2018年408真题】设有一个 12*12 对称矩阵 M 的上三角部分的元素 (1 ≤ i ≤ j ≤ 10) 按行优先存入 C 语言的一维数组 N 中, 元素 在 N 中的下标是( A )。 A. 50 B. 51 C. 55 D. 66
解: 在 C 语言中,数组 N 的下标从 0 开始。
第一个元素 对应存入,矩阵 M 的第一行有 12 元素,第二行有 11 个,第三行有 10 个,第四行有 9 个,第五行有 8 个,所以 是第 12 + 11 + 10 + 9 + 8 + 1 = 51 个元素。
下标应为 50。
4、【2020年408真题】将一个10*10 对称矩阵 M 的上三角部分的元素 (1 ≤ i ≤ j ≤ 12) 按列优先存入 C 语言的一维数组 N 中, 元素 在 N 中的下标是( C )。 A. 15 B. 16 C. 22 D. 23
解: 因为是对称矩阵,要求元素 在 N 中的下标,即求元素 在 N 中的下标。
在 C 语言中,数组 N 的下标从 0 开始。
上三角矩阵按列优先存储,先存储只有 1 个元素的第一列, 再存储有 2 个元素的第二列,以此类推。在 之前存有 第 1 列: 1 第 2 列: 2 .... 第 6 列: 6 第 7 列: 1
前面共存储有 1 + 2 + 3 + 4 + 5 + 6 + 1 = 22 个元素 ( 数组下标范围为0 ~ 21 ),注意数组下标从 0 开始,故 在数组N中的下标为 22,即 在数组 N 中的下标为 22。
2.3三对角矩阵
三对角矩阵又称带状矩阵。

在三对角矩阵中,所有非零元素都集中在以主对角线为中心的 3 条对角线的区域,其他区域的元素都为零。
采用压缩存储,将 3 条对角线上的元素,按行优先方式存放在一维数组 B 中,且 a_{1,1} 存放于 B[0]中,其存储形式如下所示:
- ❗按照行优先原则, → B[k]。(1 ≤ i, j ≤ 100, |i - j| ≤ 1)
前 i-1 行共 3(i-1)-1 个元素。 是 i 行第 j-i+2 个元素。
所以 是第 2i+j-2 个元素,数组下标从 0 开始,所以:
如果是下标从 1 开始,那么:
- B[k] → 。已知 B[k] 是第 k+1 个元素,判断 i 和 j 的位置。
前 i-1 行共 3(i-1)-1 个元素。 前 i 行共有 3i-1 个元素。
所以(注意k+1 ≤ 3i-1):
通过向上取整即可满足“刚好”大于等于:
同理,也可以使得
通过向下取整即可满足“刚好”小于等于:
计算出 i 之后,通过前面计算的 k=2i+j-3 ,得:
【考研】数据结构——特殊矩阵的压缩存储(含真题)-CSDN博客
例1、【2016统考真题】有一个 100 阶的三对角矩阵 M,其元素 (1 ≤ i, j ≤ 100)按行优先依次压缩存入标从 0 开始的一维数组中 N。元素 在 N 中的下标是( B )
A. 86 B. 87 C. 88 D. 89 解:三对角矩阵 A 如下所示:
(在三对角矩阵中,所有非零元素都集中在以主对角线为中心的 3 条对角线的区域,其他区域的元素都为零。)
采用压缩存储,将 3 条对角线上的元素,按行优先方式存放在一维数组 B 中,且 a_{1,1} 存放于 B[0]中,其存储形式如下所示:
可以计算矩阵 A 中 3 条对角线上的元素 (1 ≤ i, j ≤ 100, |i - j| ≤ 1)在一维数组 B 中存放的下标为 k = 2i + j - 3。(下标从 0 开始)
解法一:针对该题,仅需将数字逐一代入公式: k = 2 x 30 + 30 - 3 = 87,结果为87。
解法二:观察上图的三对角矩阵不难发现,第一行有两个元素,剩下的在元素 所在行之前的 28 行(注意下标 1 ≤ i,j ≤ 100)中,每行都有 3 个元素,而 之前仅有一个元素 , 不难发现元素 在数组 N 中的下标是 2 + 28x3 + 2 - 1 = 87。
(解法二中,减一是因为一维数组 B 的下标是从 0 开始。)
【注意】
解法一中的一维数组 B[k] 的下标是从 0 开始。若是从 1 开始,则公式应为 k = 2i + j - 2。
反过来,求 i , j ,有表如下:(三对角矩阵 A 从 1 开始)
例2、将三对角矩阵 A[1..100] 按行优先存入一维数组 B[1..298] 中,A 中元素 A[66][65] 在数组B 中的位置 k 为( B ) A. 198 B. 195 C.197 D.196
解:一维数组 B[k] 的下标是从 1 开始。由公式 k = 2i + j - 2,得 k = 2*66 + 65 - 2 = 195。
【另】反过来推导:已知 k 为 195 , 求 i , j:
2.4稀疏矩阵
稀疏矩阵:矩阵中非零元素的个数 t,相对矩阵元素的个数 s 来说非常少,即 s >> t (s远大于t)的矩阵。

压缩存储策略
- 顺序存储——三元组。非零元素及其相应的行和列构成个三元组(行标,列标,值),即三元组表的结点存储了行 row、列 col、值 value 三种信息,是主要用来存储稀疏矩阵的一种数据结构。
【2023年408真题】只有这三个无法判断稀疏矩阵的大小,所以加入保存行数、列数,此外还可以保存非零元素个数,以此来比较不同的稀疏矩阵。
- 链式存储——十字链表。将行单链表和列单链表结合起来存储稀疏矩阵。邻接矩阵空间复杂度达,不适合于存储稀疏矩阵。

- 二叉链表又名左孩子右兄弟表示法,可用于表示树或森林。
缺点:丧失了随机存储的特性。
例1、【2017统考真题】适用于压缩存储稀疏矩阵的两种存储结构是( A )。 A. 三元组表和十字链表 B. 三元组表和邻接矩阵 C. 十字链表和二叉链表 D. 邻接矩阵和十字链表
解:A正确。