从《Hadoop: The Definitive Guide》一书中得到一段话,如下:
“放气 将数据存储为一系列压缩 block 。问题是每个 block 的开始 不以任何允许读者位于任意位置的方式进行区分 指向流中前进到下一个 block 的开头,从而同步 本身随流。因此,gzip 不支持拆分。”
我的问题是我无法理解作者解释为什么gzip不支持拆分的原因。有人可以给我更详细的解释吗?
据我了解,如果将大文件拆分为 16 个 block 。当一个mapper开始读取一个block时,此时可能会发生2种情况:
- 映射器不能阻塞
- 或者它可以读取它然后处理它但不知道将结果放到整个流的哪里
上述情况是会发生还是不会发生还有其他逻辑?
最佳答案
为了将文件拆分成多个部分进行处理,您需要做两件事:
- 这些片段需要能够独立处理。
- 您需要能够找到拆分的位置。
正常使用的 deflate 格式两者都不支持。对于 1:deflate 格式本质上是串行的,每个匹配项都引用以前未压缩的数据,它本身可能来自类似的反向引用,可能一直到文件的开头。
您引用的描述没有提到这一点。
虽然这是一个有争议的问题,因为您没有 1,但对于 2:deflate 在流中没有明显的标记来识别 block 边界。要找到 block 边界,您必须解码边界之前的所有位,这将破坏拆分文件以进行独立处理的目的。
这就是您引用的描述中提到的要点。
虽然这对于不准备拆分的普通放气流都是正确的,但如果您愿意,可以准备这样的放气流。可以使用 Z_FULL_FLUSH
在选定的断点处删除历史记录,这允许从该点独立解压缩。它还插入一个可见标记 00 00 ff ff
。这不是一个很长的标记,可能会意外出现在压缩数据中。可以在第二次刷新后插入第二个标记,给出九个字节:00 00 ff ff 00 00 00 ff ff
。这是 Hadoop 可以使用 split the deflate stream 的东西。
关于hadoop - 为什么 gzip 不支持拆分,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38298863/