文件压缩是一种减少文件在磁盘上占用空间的技术,方便文件传输和备份工作。另外在互联网上,web传输数据都是经过压缩的,防止大文件占用带宽,一般都是在传输端进行压缩,在接收PC上进行解压缩。
我们平常所使用的文件,其中占用的空间很多都是浪费的,并没有实际的用途,只是为了计算机能够进行存储,例如我们在计算机中存储一个数字1,以一个字节计算,存储的内容类似于下面这个结构
实际上有用的位数只有最右侧的一位,左侧的7位都是浪费的,那我们就可以将这7位浪费的空间进行再利用,再举一个例子
上面这种情况,存储了8个1,那么完全可以不这么存储,不必要浪费这8bit的空间,直接存储8个1即可,这种空间上的直接压缩带来的便利就是减少文件在硬盘上的占用空间。
市面上的压缩软件就是用来干这些的,他们会将文件重新编码,压缩空间,压缩和解压缩需要使用同一种工具,不同工具可能会乱码。
推荐一款windows上的压缩与解压缩软件bindzip
linux上的文件压缩
在linux上常用压缩文件扩展名为.Z,.gz,.bz2,.xz,.tag.gz,.tag.bz2,.tar.xz,至于.zip压缩格式,是由于linux为了兼容windows,而支持的压缩格式。
补充:linux上的文件扩展名没有实际的意义,它和windows不同,但是linux为了让使用者明白文件的意义,在逻辑上还会使用扩展名标识文件,通俗的来说就是linux不认文件扩展名,但是使用者需要根据扩展名知道文件是干嘛用的
以下为linux上各压缩格式和对应的压缩软件
.Z compress对应的压缩软件
.zip zip对应的压缩软件
.gz gzip对应的压缩软件
.bz2 bzip2对应的压缩软件
.xz xz对应的压缩软件
.tag.gz tar打包,且gzip压缩
.tag.bz2 tar打包,且bzip2压缩
.tag.xz tar打包,且xz压缩
.Z格式的文件,是linux老一代的压缩软件compress压缩的,目前已经被抛弃了,如果你还有这样格式的文件的话,可以使用gzip对其进行解压,gzip可以解压.zip和.Z以及.gz格式的文件
单一文件压缩
像compress、gzip、bzip2、xz只能压缩单一文件,即不能压缩文件夹。
gzip
选择/proc/meminfo进行压缩,将/proc/meminfo复制到/tmp文件夹下
[root@VM-8-15-centos tmp]# cp /proc/meminfo /tmp
对meminfo进行压缩
[root@VM-8-15-centos tmp]# gzip meminfo
[root@VM-8-15-centos tmp]# ls
meminfo.gz
可以看到,使用gzip压缩后,源文件不见了,而只剩下了被压缩后的文件
# 使用此选项,可以将meminfo压缩后文件进行输出,即输出meminfo.gz文件,
# 输出的为二进制文件,此处并没有对meminfo进行真正的压缩
[root@VM-8-15-centos tmp]# gzip -c meminfo
# 你也可能会问这有什么用,那好,玩一个花哨的压缩文件方法
[root@VM-8-15-centos tmp]# gzip -c meminfo > meminfo.gz
[root@VM-8-15-centos tmp]# ls
meminfo meminfo.gz
# 这样不就可以在压缩文件的同时,保留源文件,然后又可以对压缩的文件进行重新命名了
解压文件
[root@VM-8-15-centos tmp]# gzip -d meminfo.gz
指定文件的压缩等级
[root@VM-8-15-centos tmp]# gzip -c1 meminfo > meminfo.gz
[root@VM-8-15-centos tmp]# gzip -c9 meminfo > meminfo1.gz
[root@VM-8-15-centos tmp]# ll
total 12
-r--r--r-- 1 root root 1310 Jul 29 15:05 meminfo
-rw-r--r-- 1 root root 520 Jul 29 15:05 meminfo1.gz
-rw-r--r-- 1 root root 556 Jul 29 15:05 meminfo.gz
# 可以看到,低等级的压缩和高等级的压缩,使用高等级的压缩后,
# 压缩文件的空间小,但是压缩过程中耗时长,低等级的相反
zcat、zmore、zless、zgrep
有这样一个场景,我们想查看压缩文件的内容,但是又不想将文件解压,那么就可以使用zcat等命令,还是上面的meminfo.gz文件
[root@VM-8-15-centos tmp]# zcat meminfo.gz
MemTotal: 1882008 kB
MemFree: 109572 kB
MemAvailable: 1351120 kB
Buffers: 128088 kB
Cached: 1208692 kB
SwapCached: 0 kB
Active: 886096 kB
Inactive: 674236 kB
Active(anon): 232560 kB
Inactive(anon): 268 kB
# 省略
.....
另外,也可以使用zgrep进行匹配
# 例如匹配上面文件中的MemTotal,同样不需要压缩
[root@VM-8-15-centos tmp]# zgrep -n MemTotal meminfo.gz
1:MemTotal: 1882008 kB
bzip2
之所以引入bzip2,是因为部分人不满足gzip的压缩率,bzip2的压缩率会高于gzip,但是压缩时间也大于gzip,牺牲时间换区空间吗。
其实bzip2的使用和gzip没有太大的区别,但是需要注意的是,在bzip2中,引入了-k选项,可以在压缩的过程中保留源文件。
bzcat、bzless、bzmore、bzgrep
同gzip使用
xz
xz追求的是更极致的压缩比,压缩比高于bzip2,用法与gzip和bzip2几乎相同
展示压缩后的文件的详细信息
[root@VM-8-15-centos tmp]# xz -l meminfo.xz
Strms Blocks Compressed Uncompressed Ratio Check Filename
1 1 548 B 1,310 B 0.418 CRC64 meminfo.xz
xzcat、xzless、xzmore、xzgrep
同gzip使用
gzip、bzip2、xz区别
- 三者都是压缩文件使用的命令,且只能压缩单一文件
- 三个只是压缩比不同、压缩时使用的时间不同
三者的压缩比gzip < bzip2 < xz
三者压缩的时间gzip < bzip2 < xz
使用建议:当压缩大文件且对时间没有太大的要求时,可以使用xz,这样有利于节省空间。如果对时间要求比较高,但是对空间没有太大的要求时,可以使用gzip或bzip2。
多文件打包压缩
上面我们谈到的都是针对单一的文件进行压缩,但是我们在linux中如果有压缩多个文件怎么办,那我们可以先对多个文件进行打包,然后进行压缩。
上面提到的打包工具就是tar,他可以将多个文件打成一个包。
先练习一下对多个文件打包压缩操作
[root@VM-8-15-centos tmp]# ls
test
[root@VM-8-15-centos tmp]# tar -zcv -f test.tar.gz test/
test/
test/meminfo.bz2
test/meminfo.xz
test/stargate.lock
test/meminfo.gz
[root@VM-8-15-centos tmp]# tar -jcv -f test.tar.bz2 test
test/
test/meminfo.bz2
test/meminfo.xz
test/stargate.lock
test/meminfo.gz
[root@VM-8-15-centos tmp]# tar -Jcv -f test.tar.xz test
test/
test/meminfo.bz2
test/meminfo.xz
test/stargate.lock
test/meminfo.gz
[root@VM-8-15-centos tmp]# ls
test test.tar.bz2 test.tar.gz test.tar.xz
上面操作中需要注意的是,我们需要自己指定被压缩后的文件名,所以一定要注意文件名的可读性,可不敢乱写,使用gzip压缩的后缀为.tar.gz,使用bzip2压缩的后缀为.tar.bz2,使用xz压缩的后缀为.tar.xz。
另外,-f选项尽量单独拿出来,不要与其他选项写在一起,例如tar -zcfv test.tar.gz test,这样执行之后会报错,至于原因,因为-f后接的是文件名,所以命令就不可执行了,尽量养成好的习惯。
# 查看压缩后文件里的内容
[root@VM-8-15-centos tmp]# tar -t -f test.tar.gz
test/
test/meminfo.bz2
test/meminfo.xz
test/stargate.lock
test/meminfo.gz
可以看到,压缩后的文件里,路径都是相对路径,这么做有什么好处呢,比如我们在/tmp下解压这个文件,那么这些解压出来的文件都是相对于/tmp的路径,但是如果带绝对路径压缩呢,这样当我我们解压的时候,就会把这些文件自动放到了这个绝对路径,如果是备份文件,那带绝对路径解压的时候岂不是覆盖了原有的文件,这显然不是我们想要的。
补充:在Ubuntu18.04以及centos7上进行测试,即使指定了-P,也不会带绝对路径,想必这是为了安全考虑吧
解压到指定目录
我们有时候想要将一个文件解压到指定的目录,例如将我们上述打包的test.tar.gz文件解压到家目录下,此时我们在/tmp目录下,我们还需要cd到家目录,然后将文件移动到家目录进行解压,岂不是很麻烦,可以使用-C选项,直接解压到指定的目录
[root@VM-8-15-centos tmp]# tar -zxv -f test.tar.gz -C /root/
test/
test/meminfo.bz2
test/meminfo.xz
test/stargate.lock
test/meminfo.gz
[root@VM-8-15-centos tmp]# cd /root/test/
[root@VM-8-15-centos test]# ls
meminfo.bz2 meminfo.gz meminfo.xz stargate.lock
解压部分文件
有时候,我们只想解压压缩包内的一部分甚至一个文件,可以这样做
# 先查看压缩包内都有哪些文件,找到自己想解压的那个
[root@VM-8-15-centos tmp]# tar -t -f test.tar.gz
test/
test/meminfo.bz2
test/meminfo.xz
test/stargate.lock
test/meminfo.gz
# 进行解压
[root@VM-8-15-centos tmp]# tar -zxv -f test.tar.gz test/stargate.lock
test/stargate.lock
[root@VM-8-15-centos tmp]# ls
stargate.lock test testp.tar.gz testP.tar.gz test.tar.bz2 test.tar.gz test.tar.xz v
[root@VM-8-15-centos tmp]# cd test/
[root@VM-8-15-centos test]# ls
stargate.lock
只需要在解压时,单独指定要解压的文件名即可
tar -[zjJ]xv -f filename target-name
打包时将某些文件排除
打包时,如果不想将某些文件进行压缩,则可以使用--exclude选项进行排除
[root@VM-8-15-centos tmp]# tar -zcv -f test.tar.gz --exclude=test/stargate.lock test
test/
test/meminfo.bz2
test/meminfo.xz
test/test.tar.gz
test/meminfo.gz
注意:在排除路径后写东西,一定要写相对路径。
备份最新的文件
我们在备份的时候,总是想将最新的文件放入到压缩包内,而一些旧的文件不需要重新打包,那我们就可以在打包时指定时间,直将最新的文件打包,此处我们指定mtime
[root@VM-8-15-centos tmp]# tar -zcv -f test1.tag.gz --newer-mtime="2021/07/29 17:31:00" test
tar: Option --newer-mtime: Treating date `2021/07/29 17:31:00' as 2021-07-29 17:31:00
test/
tar: test/b.txt: file is unchanged; not dumped
test/a.txt
tar: test/c.txt: file is unchanged; not dumped
tarfile与tarball
tarfile:使用tar打包后,此时还没有进行压缩,此时的包文件叫做tarfile
tarball:tar打包后,使用gzip、bzip2、xz进行压缩后,此时的文件叫做tarball