在文件中间插入一个字节块而不重写所有内容?
Posted
技术标签:
【中文标题】在文件中间插入一个字节块而不重写所有内容?【英文标题】:Inserting a block of bytes in the middle of a file without rewriting everything? 【发布时间】:2021-11-13 10:23:41 【问题描述】:由于文件是作为块存储在磁盘上的,是否可以在块链的中间插入一个块?
这是因为,如果没有这样的 API,如果我想在文件中间的某个位置插入一个 4kb 的块,使用传统的读/写 api,我基本上必须在之后重写文件中的所有内容该位置并将它们移动 4kb。
我可以接受仅适用于 some 操作系统或 some 文件系统的答案。它不必跨平台或适用于每个文件系统。
(我也了解并非所有文件系统或硬件都使用 4kb 的块 - 适用于不同数字的答案也可以)。
【问题讨论】:
传统上没有办法做到这一点。最近这里有一篇关于 SO 的帖子,关于一个新的 Linux API,它可以让你这样做,尽管只适用于某些底层文件系统类型。不幸的是,我不记得细节了。 见this answer。 (所以也许不是最近,也不是那么“新”!) 【参考方案1】:我不确定允许在中间轻松扩展文件的文件系统。再说一次,许多现代文件系统实际上并没有块链。块链是 FAT 文件系统家族的东西。相反,现代文件系统中的块通常被组织成一棵树。在树中,您可以找到包含 O(lg n) 读取中任何字节位置的块,对数具有如此大的底数,可以认为它基本上是恒定的。
虽然链可以比较容易地允许“在中间插入 n 个块”的操作,但不幸的是树没有。这并不意味着树是错误的结构 - 相反,许多数据库系统从它提供的快速随机访问中受益匪浅。
请注意,树使您能够拥有其他可能有用的东西而不是孔 - Unix 文件系统有 sparse files - 已知包含零的文件的任何块都不需要实际使用磁盘空间 - 相反这些块被标记为未分配并被认为在树结构本身中包含零。
【讨论】:
有趣。所以我一般可以假设读取 3 个随机块和读取 3 个连续块将具有大致相同的性能特征? @hasen 仅在 SSD 上。如果块分散在周围,HDD 仍然需要移动它的头部。这当然会忽略磁盘缓存以及您关心的数据是否已经在其中。也许“这取决于”会更正确。以上是关于在文件中间插入一个字节块而不重写所有内容?的主要内容,如果未能解决你的问题,请参考以下文章
Python Pandas - 编写新的 CSV 标题行而不读取/重写整个文件