我想创建 tar gzip 存档,但要以与最常用方式相反的方式执行 - 单独压缩存档中的文件,而不是压缩整个存档:这样它就可以保留应有的可搜索属性。这对我来说更有意义,我不知道为什么没有人喜欢它。
我对如何做到这一点有一些想法:
- 使用具有压缩功能的存档工具,例如 7zip
- 编写自己的脚本来执行此操作,首先压缩文件,然后将其提供给 tar (已经找到一个方便的 Python 脚本来编写 tar 文件和Python gzip 库似乎很容易使用。
但是,理想情况下,我希望继续使用 tar,因为它是我工作中熟悉的、事实上的归档工具。tar 有一个开关--to-command
,允许将提取的文件通过管道传输到程序。如果我有一个对称命令,例如,--from-command
我可以轻松地实现我的愿望:
tar cf my_archive.tar file1 file2 --from-command=gzip
tar xf my_archive.tar --to-command=gunzip
我的动机来自于处理包含大量大文件的档案。我目前对它们进行 tar-gzip 压缩,但从档案中提取任何文件都需要很长时间 - 需要先解压缩,然后 tar 才能访问该文件,而且它是以串行方式执行的!
我的问题是:
- 是否存在一种明显的方法可以实现这一点而我却忽略了?
- 是否有人已经编写过与之相关的工具,特别是
tar
? - 如果有人调用
tar
和gzip
在 Linux 中归档和压缩的标准方法,那么以我提到的方式进行压缩归档的等效、流行的方法是什么(即不是tar.gz
) - 是否有其他我忽略的方法来避免从大型 tar-gzip 存档中提取文件所需的大量时间?
谢谢!
编辑
我意识到我需要重新措辞并完善我的问题。特别是因为,正如罗宾汉指出的那样,存在相当简单的解决方案来创建压缩档案(即zip
)。所以这里是:
有没有办法tar
可以真正随机访问存档,同时仍保持压缩状态?如果没有,是否有另一个tar
Linux 替代品(以相同的原理构建,理想情况下,支持相同的命令行选项)可以实现这一点?
现在我可以通过以下方式tar
从一般意义上用进行替换zip
:
tar c path/to/file1 path/to/file2 | gzip > arc.tar.gz
gunzip < arc.tar.gz | tar x
到:
zip -qr - path/to/file1 path/to/file2 > arc.zip
unzip -qoX test.zip
tar
然而,它的缺点是它不支持所有用于归档的选项,即:
- 将每个提取的文件分别传输到管道(
--to-command
开关) unzip
不接受标准输入中的档案。funzip
但是 - 它只输出第一的档案中的文件
因此它相当有限。
再次感谢!
答案1
我已经多次阅读了您的问题,很难理解,但我想我现在明白了。您希望将文件放入单独的 tar 存档中,然后将它们全部存储在一个 gz 存档中。这行不通,因为 gz 存档仅支持压缩 1 个文件,这就是人们在使用 gz 压缩之前将文件打包成 tar 的原因。您可以做相反的事情,将每个文件放入一个 gz 存档中,然后将所有 gz 存档放入一个 tar 存档中。或者,您可以停止使用需要双重存档的格式,并使用支持多个文件的存档格式,例如 zip。
压缩 tar 内的文件仍会导致对 gz 档案的顺序访问,因为 tar 格式不支持随机访问。Zip 档案使用集中式目录,因此无需解压或读取整个档案即可进行随机文件访问。我在 Linux 下不经常进行存档,但在 Windows 上,我喜欢使用 7-zip 创建带有 lzma 压缩的 zip 档案。值得注意的是,这两种方法在与 tar.gz 相当的压缩率一起使用时,由于缺乏可靠的压缩,会产生更大的档案,这就是为什么 tar.gz 在 Linux 世界中比 zip 更受欢迎的原因,用于分发软件。
创建一系列 GZ 档案并存储在 Tar 档案中:
cp -a -n -v "/home/me/example/inputfiles/." --target-directory="/home/me/example/gzfiles"
这会将您想要存档的文件复制到另一个文件夹。Gunzip 不允许保留原始未存档文件,但使用副本可以避免这种情况。
gzip -9 “/home/me/example/gzfiles/*”
这将为每个文件创建一个单独的 gz 存档,并使用最大压缩率。如果您的系统无法处理,请尝试较低的数字;默认数字为 6。
tar -cf "/home/me/example/tar/archive.tar" -C "/home/me/example/gzfiles 。"
这将创建一个包含所有 gz 档案的 tar 档案。
从 Tar 存档中的 GZ 存档中提取单个文件:
sudo apt-get 安装 archivemount
这将安装 archive mount,一个可以将 tar 文件挂载到目录的工具。
archivemount -o readonly "/home/me/example/tar/archive.tar" "/home/me/example/mount"
这将挂载 tar 存档,以便您可以提取所需的 gz 存档。我相信可以使用 tar 从 tar 存档中提取单个文件,但我不知道该命令,因此我使用这种方法。
gunzip -c "/home/me/example/mount/example1.txt.gz" > "/home/me/example/extract1/example1.txt"
这将提取文件。Gunzip 仅支持提取到源目录或标准输出,因此在此命令中我们使用了标准输出,然后将输出通过管道传输到文件。
sudo umount“/home/me/example/mount”
这将卸载 tar 存档。
从 Tar 存档中的一系列 GZ 存档中提取所有文件:
cd“/home/me/example/extractall”
由于 tar 会提取到当前目录,因此这会将终端放入您想要提取到的目录中。
tar -xf /home/me/example/tar/archive.tar
这将提取 gz 档案。
gunzip *.gz
这会将 gz 档案的内容提取到当前目录/home/me/example/extractall/
并删除 gz 档案。
创建 ZIP 存档:
cd“/home/me/example/inputfiles”
这会将终端放入输入文件目录中,因为 zip 会从当前目录创建一个档案并保存到其中。
zip -9 -r 输入文件输入文件.zip *
这将创建所有输入文件目录内容(不包括隐藏文件)的 zip 存档,并使用最大压缩。如果您需要高压缩,p7-zip 将是更好的工具。
mv "/home/me/example/inputfiles/inputfiles.zip" "/home/me/example/zip/archive.zip"
这将允许您随意重命名档案,并将其移动到您想要的位置。
提取 ZIP 档案:
cd“/home/me/example/zip”
这会将终端放入包含 zip 的目录中。
解压缩-n 档案.zip
这会将 zip 档案内容提取到当前目录。
答案2
如果你想要的是档案中具有随机访问功能的单独压缩文件,那么達爾(“磁盘存档”)可能就是您要找的东西。较新的版本支持 LZMA 压缩,这是 7-Zip 使用的算法。还可以定义过滤器以存储某些未压缩的文件类型并节省时间,例如媒体文件和已经具有自身压缩的存档。我最喜欢的功能是压缩现有(未压缩)存档,这样我就可以快速备份并在更方便的时间或在更强大的机器上运行 CPU 密集型 LZMA 压缩:
dar --empty-dir \
--fs-root /home \
--create home-backup-2016-01-11 \
--prune lost+found
然后稍后和/或其他地方:
dar -+ home-backup-2016-01-11-compressed-encrypted \
-A home-backup-2016-01-11 \
-zxz:6 \
-K "aes:" \
-an -ag -Z "*.mpg" -Z "*.avi" -Z "*.flac" -Z "*.cr2" \
-Z "*.vob" -Z "*.jpg" -Z "*.jpeg" -Z "*.mpeg" -Z "*.png" \
-Z "*.mp3" -Z "*.ogg" -Z "*.deb" -Z "*.tgz" -Z "*.tbz2" \
-Z "*.rpm" -Z "*.xpi" -Z "*.run" -Z "*.sis" -Z "*.gz" \
-Z "*.Z" -Z "*.bz2" -Z "*.zip" -Z "*.jar" -Z "*.rar" \
-Z "*.xz" -Z "*.dar" -Z "*.7z" -acase
如上所示,加密也是可能的,同时仍允许提取单个文件。但是,dar 似乎没有与 等效的功能--to-command
。从您的问题很难判断您是否打算将该功能用于除解压之外的其他用途。
(是的,我知道这个问题已经很老了。这是为那些像我一样,在 Google 上搜索“tar 单独压缩”并得到这个结果的人准备的。)