我必须存储两个非常大的文件A和B(如100GB)。然而,B在大部件中可能与A类似,因此我可以存储A和diff(A,B)。这个问题有两个有趣的方面:
我目前在如何计算在这些条件下从A到B的增量时感到茫然。有谁知道这个算法?
同样,问题很简单:编写一个算法,可以用尽可能少的字节存储文件A和B,因为两者都非常相似。
附加信息:虽然大部件可能相同,但它们可能具有不同的偏移并且可能出现故障。最后一个事实是为什么传统的差异可能不会节省太多。
答案 0 :(得分:16)
您可以使用rdiff
,它可以很好地处理大文件。在这里,我创建了两个大文件A
和B
的差异:
创建一个文件的签名,例如
rdiff signature A sig.txt
使用生成的签名文件sig.txt
和另一个大文件,创建增量:
rdiff delta sig.txt B delta
现在delta
包含B
和A
时重新创建文件delta
所需的所有信息。要重新创建B,请运行
rdiff patch A delta B
在Ubuntu中,只需运行sudo apt-get install rdiff
即可安装它。它非常快,我的PC每秒大约40 MB。我刚刚在8GB文件上试过它,rsync使用的内存大约是1MB。
答案 1 :(得分:13)
看看RSYNCs算法,因为它的设计非常适合这样做,因此它可以有效地复制增量。我记得,这个算法已经很好地记录了。
答案 2 :(得分:8)
这正是称为"data deduplication"的问题。最常用的方法是:
这种重复数据删除算法并不像xdelta,但对于大型数据集来说速度更快,可扩展性更高。分块和指纹识别以每个核心约50 MB / s(Java)执行。索引大小取决于冗余,块大小和数据大小。对于200 GB,它应该适合存储器以用于例如大小的块大小。 16KB。
Bentleys and Mciloys压缩方法非常相似(例如由Googles BigTable使用),但我不知道任何使用压缩技术的开箱即用命令行工具。
"fs-c"开源项目包含大部分必要的代码。但是,fs-c本身只会尝试在内存中或使用Hadoop群集来测量冗余和analzye文件。
答案 3 :(得分:6)
一个问题是文件中的记录大小是多少,即偏移量可以逐字节更改,还是文件包含1024B块。假设数据是面向字节的,您可以执行以下操作:
为文件A创建一个后缀数组。这个数组是文件A的所有索引值的排列。如果A有2 ^ 37个字节,那么索引数组最容易用64位整数表示,所以每个字节(文件的偏移量)对应于索引数组中的8个字节,因此索引数组将长2 ^ 40个字节。例如。比方说800 GB。例如,您也可以仅为每个第1024个位置编制索引,以减小索引数组的大小。这样就可以根据可复制片段的平均运行时间来确定包装质量。
现在贪婪地打包从偏头o = 0开始的文件B,然后使用索引数组找到A中与“o”开头的数据匹配的最长匹配。您在打包文件中输出该对。这样就可以在没有任何编码16字节的情况下使用,所以如果运行是<你实际上丢失了16个字节的空间这可以通过使用随后的位级编码并使用位标记来标记是否编码隔离字节(标记+ 8位= 9位)或偏移/长度对(标记+ 40位+ 40位= 81)来轻松解决比特),比方说。将最长的片段打包到o后,将o增加到片段后的下一个字节,然后重复到文件末尾。
后缀数组的构造和使用很简单,您应该很容易找到参考。在高速应用程序中,人们使用后缀树或后缀尝试,这些操作更复杂但提供更快的查找。在您的情况下,您将在二级存储上使用该阵列,如果打包阶段的运行速度不是问题,则后缀数组应该足够。
答案 4 :(得分:1)