我的知识记录

Python批量压缩文件为zip教程:一行命令搞定多文件打包

用Python标准库zipfile批量把指定目录下的文件压缩成zip包,支持按类型筛选、保留目录结构,无需安装第三方库,完整代码可直接运行。

场景痛点

工作中经常需要把一堆报表、合同、图片打包成一个zip发给同事。手动框选、右键压缩,文件一多就容易漏选或多选,遇到同名文件还会弹提示打断操作。用Python写个脚本,指定源目录和输出路径,几秒就能把目标文件全部装进一个zip包,结果稳定可复现。

用到的库

本篇全部使用Python标准库,无需pip安装:

zipfile   # 读写zip压缩包
pathlib   # 跨平台路径处理

完整代码

import zipfile
from pathlib import Path


def zip_files(source_dir: str, output_zip: str, suffix_filter: list = None) -> str:
"""
批量压缩指定目录下的文件为zip
:param source_dir: 源目录路径
:param output_zip: 输出zip文件路径
:param suffix_filter: 只压缩指定后缀,如 ['.xlsx', '.pdf'];None表示全部
:return: 生成的zip路径
"""
src = Path(source_dir)
out = Path(output_zip)
out.parent.mkdir(parents=True, exist_ok=True)

count = 0
# ZIP_DEFLATED 表示使用压缩算法,ZIP_STORED 表示仅打包不压缩
with zipfile.ZipFile(out, 'w', zipfile.ZIP_DEFLATED) as zf:
for file in src.rglob('*'):
if not file.is_file():
continue
# 按后缀过滤
if suffix_filter and file.suffix.lower() not in suffix_filter:
continue
# arcname 控制压缩包内的相对路径,避免把绝对路径打进去
arcname = file.relative_to(src)
zf.write(file, arcname=arcname)
count += 1

print(f"压缩完成,共打包 {count} 个文件 -> {out.resolve()}")
return str(out)


if __name__ == "__main__":
# 示例:把 D:/reports 下所有 xlsx 和 pdf 打包成 daily.zip
zip_files(
source_dir="./reports",
output_zip="./output/daily.zip",
suffix_filter=['.xlsx', '.pdf']
)

代码讲解

  • zipfile.ZipFile(out, 'w', zipfile.ZIP_DEFLATED):以写入模式打开zip对象,ZIP_DEFLATED表示启用DEFLATE压缩算法,文件体积更小;如果想不压缩只打包,换成ZIP_STORED
  • src.rglob('*'):递归遍历源目录下所有文件和子目录,rglob是pathlib提供的递归通配方法。
  • file.relative_to(src):计算文件相对于源目录的路径,作为压缩包内的arcname。这样解压后不会带上C:\Users\...这种绝对路径。
  • suffix_filter参数:传入后缀列表可以只打包指定类型的文件,不传则打包全部文件。

运行结果

运行后会在output/目录下生成daily.zip。用解压软件打开可以看到按原目录结构组织的文件列表,命令行同时打印打包的文件数量。

注意事项

  • 压缩包内中文文件名在Windows资源管理器里偶尔会乱码,这是zip格式历史编码问题。如需兼容老旧解压软件,可在ZipFile构造时指定metadata_encoding='utf-8'(Python 3.11+支持)。
  • suffix_filter只过滤后缀,不匹配目录。如果要排除某个子目录,需要在循环里加判断。
  • 源目录里如果本身已经有zip文件,会被一起打进去,造成嵌套压缩。建议过滤掉.zip后缀。

Python批量压缩文件为zip教程:一行命令搞定多文件打包

标签:

更新时间:2026-09-14 21:24:33

上一篇:Python清理临时文件过期文件:按天数自动删除旧文件

下一篇:Python批量校验文件是否损坏教程