运行

时间:2016-12-12 21:43:17

标签: c sparse-matrix

在实施"搜索窗口"对于C中的快速动态时间扭曲,我需要构建一个表示具有非常特殊结构的稀疏二进制矩阵的结构。

这个矩阵对它有一些强烈的结构约束:具体来说,只有一个"运行"每行非零数据,尽管该运行长度可变。随着行的增加,起始单元格的列索引和结束单元格列索引的值单调增加:

示例有效矩阵(* =已填充,。=未填充)

  0 1 2 3 4 5
0 * * * . . .
1 . * * * . .
2 . * * * . .
3 . . * * * *
4 . . * * * *


  0 1 2 3 4 5
0 * * * * . .
1 . * * * * .
2 . . * * * .
3 . . . . * *
4 . . . . . *

无效矩阵示例:

  0 1 2 3 4 5
0 * * * . * * <-- more than one continuous run
1 . * * * . .
2 . * * * . .
3 . . * * * *
4 . . * * * *

  0 1 2 3 4 5
0 * * * . . .
1 . * * * . .
2 . * * * . .
3 * * * * * * <-- start index not monotonically increasing
4 . . * * * *


  0 1 2 3 4 5
0 * * * . . .
1 . * * * * .
2 . * * * . . <-- end index not monotonically increasing
3 . . * * * *
4 . . * * * *

这些稀疏矩阵主要填充在对角线上,但它们方形,所以我不知道我是否应该使用&#34;锯齿状对角存储&#34;。

我目前的方法是为每行存储(开始,结束)列索引:即

  0 1 2 3 4 5
0 * * * . . .
1 . * * * . .
2 . * * * . .
3 . . * * * *
4 . . * * * *

(逻辑上)存储为<​​/ p>

(0, 0) --> (0, 2)
(1, 1) --> (1, 3)
(2, 1) --> (2, 3)
(3, 2) --> (3, 5) 
(4, 2) --> (4, 5)

(虽然这些内部存储为ravelled指数,即。)

(0 * num_cols + 0) --> (0 * num_cols + 2)
(1 * num_cols + 1) --> (1 * num_cols + 3)

所以最终的结构看起来像

[0, 2, 7, 9, 13, 15, 20, 23, 26, 29]

然后,这个结构是delta编码的

[first_value, offset_1, offset_2, ...]
[0, 2, 5, 2, 4, 2, 5, 3, 3, 3] 

因为这些delta值很小且正面,我们可以利用它们将它们打包成VARINT结构的一些风格。

第一个问题:这些矩阵有一个众所周知的名字吗?似乎在文献中找不到多少。

第二个问题:这种存储方案是否利用了矩阵的所有强大属性?我可以滥用约束来以某种方式存储更少的数据吗?

我已经阅读了一些描述一般稀疏矩阵的稀疏矩阵存储的文档,但是我觉得这种特殊情况结​​构可能具有特殊情况下的最佳存储/编码方案。

1 个答案:

答案 0 :(得分:1)

我认为您考虑绝对索引值(然后使用delta编码)的方法已经产生了良好的结果,但它没有使用单调递增的开始/结束索引约束。

考虑存储的存储结构 - 相对于绝对开始和结束索引 - 只有开始和结束索引的增量应该 - 平均 - 产生具有较小范围的数字(因此表示较短)。

将您的第一个样本翻译成此结构将如下所示:

(0/2) - (1/1)(0/0)(1/2)(0/0)

其中第一对(0/2)表示绝对开始/结束 - 索引,其他对代表每行的开始和结束的增量。 由于这些数字使用较小的范围,因此可变长度整数编码应该产生更好的压缩。

例如,考虑以下(简单)整数编码:

0 .. 00
1 .. 01
2 .. 100
3 .. 101
4 .. 1100
5 .. 1101
6 and higher: 111 + 16 bit integer

使用此编码,第一个样本转换为包含22位的以下比特流:

00 100 01 01 00 00 01 100 00 00

这种方法效果越好,增量越小;当逐行考虑增量时,如果矩阵的行数多于列数,则应该是这种情况。

只是想要优化具有更多列而不是行的矩阵:可以想到使用相同的存储方法逐列;我认为(但没有数学证明)单次运行的逐行单调递增也意味着单次运行也会逐列单调递增。