一路经行处,莓苔见履痕。
大家好,我是Python进阶者。
一、前言
前几天在Python钻石交流群【海南菜同学】问了一个Python
自动化办公的问题,提问截图如下:
文件的截图如下:
这个需求其实很常见,我们平时也会在工作中经常遇到,同一个名字的文件,多次保存,会自动地增加()
,如上图所示。万一文件太多(几十个,上百个等)的时候都分不清哪个跟哪个了。挨个找起来,肯定都得抓瞎。
这里有个细节需要注意下:有时候我们在微信中反复接收、修改同一份文件,那么每次的文件都会留下备份。这些不能算是冗余的。因为本质上,他们不是同一个文件的多个重复备份。
针对这样的现实需求,这就需要我们不定期地去删除下重复文件了,基于此需求,本文基于Python编程,给出了相应的解决办法。
二、实现过程
实现的思路主要是两层判断:第一个先判断文件大小是否为相同,大小不同则不是重复文件,予以保留;第二个是判断文件大小相同再判断文件md5,如果md5相同,则是重复文件,予以删除。
基于上面的思路,我们便可以码字了。这里要感谢【瑜亮老师】提供的代码,如下所示:
代码语言:javascript复制# -*- coding:utf-8 -*-
# @Time: 2022-09-21 13:20
# @Author: 瑜亮
# 思路:两层判断:
# 1.先判断文件大小是否为相同,大小不同则不是重复文件,予以保留
# 2.文件大小相同再判断文件md5,md5相同,则是重复文件,予以删除
from pathlib import Path
import hashlib
def getmd5(filename):
# 接收文件路径,返回文件md5值
with open(filename, 'rb') as f:
data = f.read()
file_md5 = hashlib.new("md5", data).hexdigest()
return file_md5
def main():
path = r"E:data"
all_size = {}
total_file = 0
total_delete = 0
# 获取路径内的所有文件名,默认是升序排列,相同文件将会保留日期时间最新的
all_files = Path(path).glob('*.*')
# 降序排列,相同文件将会保留文件名最短的(即日期时间最久的)
all_files = sorted(all_files, reverse=True)
# 遍历文件路径内的所有文件
for file in all_files:
# 获取文件所占字节大小,作为数据字典的键
size = file.stat().st_size
# name_and_md5列表用于存储文件绝对路径和md5值,作为数据字典的值
name_and_md5 = [file, '']
# 针对重复文件进行处理,生成字典存储相关信息
# 字典all_size中key是size,value是name_and_md5列表
# 针对相同size的文件,再调用getmd5函数,获取文件的md5值
# 文件size不同(不在all_size.keys()中),则自动判断为不同的文件,予以保留
if size in all_size.keys():
# 调用getmd5函数,获取文件的md5值
new_md5 = getmd5(file)
if all_size[size][1] == '':
all_size[size][1] = getmd5(all_size[size][0])
# 判断md5值存在,即文件重复,则删除文件。md5值不存在,则把md5值加入列表中
if new_md5 in all_size[size]:
file.unlink()
total_delete = 1
else:
all_size[size].append(new_md5)
else:
all_size[size] = name_and_md5
total_file = 1
print(f'文件总数:{total_file}')
print(f'删除个数:{total_delete}')
if __name__ == '__main__':
main()
这里我自己拿一个文件夹做了一个尝试,代码运行之后,基本上几秒钟就结束了,速度非常快,如下图所示:
使用程序进行操作,比起手动的进行删除,事半功倍,Python自动化办公yyds!上述代码使用了pathlib和hashlib库分别进行了文件路径和文件大小进行了相应的判断,针对重复的文件进行了删除处理。上述代码中比较难理解的三个地方如下:
代码语言:javascript复制all_files = Path(path).glob('*.*')
size = file.stat().st_size
file.unlink()
这三处分别用到了模块中的“获取目录文件完整路径”、“获取文件字节大小”、“删除文件”,关于pathlib的应用文章,可以前往:手把手教你用Python批量实现文件夹下所有Excel文件的第二张表合并。
这个代码用了文件md5,所以是非常精确的。可以说精确的过头。就是只要文件有一丝丝的改动,都算是另外一个文件。这是【瑜亮老师】的测试文件,其实两个里面内容只相差一个回车,就会被代码认为是另外一个文件。从数据安全角度来看,文件名一样,实际上内容略有不同,这个代码也同样可以识别出来是不同文件,可以说是非常精准了!
有想法的,还可以把这个代码进行打包成一个小软件工具,发给朋友们玩玩,也是不错的哦!当然了,你还可以自动添加一个定时任务,比方说每5天之后程序自动跑一次,这样就实现了定期删除重复文件的效果啦!欢迎大家积极尝试,有做出来的话,欢迎留言支持,下一篇文章安排上墙!
如果在运行过程中,有遇到问题的话,请随时联系我进行反馈,让编程更好地助力我们的工作和生活!
三、总结
大家好,我是Python进阶者。这篇文章主要给大家分享了一个自动删除文件的小工具。感谢【瑜亮老师】提供的思路和代码,感谢群友们的积极讨论学习。