删除具有特定扩展名的文件,位于文本文件中的列表中
delete files with specific extension located as a list in a textfile
我目前正在尝试从网络服务器上清理一些媒体文件夹。问题是每个文件都以多种不同的分辨率复制,而且并非所有都相同。
例如:picture1.jpg
也有 picture1-150x150.jpg
、picture1-100x100.jpg
和 picture1-50x50.jpg
。
虽然其中很多是相同的,但也有很多是不同的。
所以我首先尝试了这个:
import os
dir_name = "path"
test = os.listdir(dir_name)
for item in test:
if item.endswith("150x150.jpg"):
os.remove(os.path.join(dir_name, item))
它完成了它的工作,但在添加各种不同的分辨率和文件扩展名(jpg、jpeg、png、etcpp)后变得非常臃肿:
if item.endswith("-150x150.jpg"):
os.remove(os.path.join(dir_name, item))
if item.endswith("-100x100.jpg"):
os.remove(os.path.join(dir_name, item))
if item.endswith("-75x75.jpeg"):
os.remove(os.path.join(dir_name, item))
if item.endswith("-50x50.jpeg"):
os.remove(os.path.join(dir_name, item))
etc...
所以我尝试将这些决议输入文本文件并将其用作列表。
import os
dir_name = "path"
folder = os.listdir(dir_name)
with open('list.txt') as f:
lines = f.read().splitlines()
for file in folder:
if file.endswith(str(lines)):
os.remove(os.path.join(dir_name, file))
虽然我能够在一定程度上阅读和修改代码,但这是我在 Google 半天后设法做到的。
因此,我恳请任何帮助或指导。
我认为您需要检查行列表
的所有元素
然后,如果文件名中出现列表行的元素,则将其删除
for file in folder:
for line in lines:
if file.endswith(str(line)):
os.remove(os.path.join(dir_name, file))
endswith 方法接受一个元组作为参数,这意味着您可以将所有扩展合并到一个变量中。
extensions = ("-150x150.jpg","-100x100.jpg","-75x75.jpeg","-50x50.jpeg")
然后你把这个变量传给endswith
if file.endswith(extensions):
os.remove(os.path.join(dir_name, file))
这是我用于概念验证的片段:
files = [
"file1",
"file2.jpg",
"file123",
"file4.jpg.old",
"file5.txt"
]
extensions = (
".jpg",
".exe",
".txt"
)
for file in files:
if file.endswith(extensions):
print(f'File :{file} should be delete')
else:
print(f'Skipping:{file}')
返回:
╰─ python3 app.py
Skipping:file1
File :file2.jpg should be delete
Skipping:file123
Skipping:file4.jpg.old
File :file5.txt should be delete
除了“-150x150.jpg”之外,是否有任何文件名中包含破折号?如果没有,您可以执行以下操作:
import os
dir_name = "path"
folder = os.listdir(dir_name)
for file in folder:
split_file_name = file.split('-')
if len(split_file_name) > 1:
os.remove(os.path.join(dir_name, file))
如果您不能保证只有一个破折号,那么我认为正则表达式将是您最好的选择。
import os
import re
dir_name = "path"
folder = os.listdir(dir_name)
pattern = re.compile('[a-zA-Z0-9_\-]+-\d+x\d+.jpg')
for file in folder:
if pattern.match(file):
os.remove(os.path.join(dir_name, file))
您可以简单地制作一个可以处理所有不同可能性的正则表达式,并使用它来过滤文件名。我使用您提供的循环编写了这个示例。您可以将其更改为循环到收集文件名所需的任何内容。这个例子的重点是正则表达式过滤器。
import re, os
dir_name = "path"
test = os.listdir(dir_name)
fmt = re.compile(r'([\w\d_]+)-\d{1,4}x\d{1,4}\.(jpg|png|jpeg|gif|bmp|tga)', re.I)
for item in test:
if fmt.search(item):
os.remove(os.path.join(dir_name, item))
如果您不理解正则表达式,这里有一个细分:
([\w\d_]+)
获取连续的单词、数字和下划线。 (例如:'my_family_pic1')。 +
表示至少应有 1 个单词、数字或下划线,但要尽可能多地连续出现。 +
的补充是 *
,它将匹配描述数据的 0 次或多次连续出现。
-\d{1,4}x\d{1,4}
获取从“-0x0”到“-9999x9999”的任何组合。 {1,4}
部分只是说应该有 1 到 4 个连续的前面描述的类型的字符。在这种情况下,该类型将是数字。
\.(jpg|png|jpeg|gif|bmp|tga)
这部分的字面意思是我们期望一个点后跟 'jpg' OR 'png' OR 'jpeg' OR... 我们必须转义点,因为正则表达式中的点意味着“任何非空白字符”,除非我们使用 re.S
标志,在这种情况下,点将匹配任何内容。通过转义它,我们告诉正则表达式我们真的只是想找到一个点。 (group)
用于包含一组可能性,隔离逻辑 and/or 隔离一段数据,可以通过其组索引直接引用。如此处所用,您可以将其视为条件语句。如果我们在此处删除分组,则正则表达式将找到 ex:'some_file-10x10.jpg' 或完全失败。遇到ex:'.png'却只找ex:'png',永远匹配不到.
当前的正则表达式只会查找文件名中具有尺寸的图像(即.. -150x150)。如果你想删除任何图片,你可以将正则表达式更改为:
fmt = re.compile(r'([^.]+)\.(jpg|png|jpeg|gif|bmp|tga)', re.I)
这将从接受每个不是(^
)点的字符开始,然后是点和扩展名。这相当于说“我们不关心开始,只要确保它以某种方式结束”。但是,如果实际文件名中有任何点,则此表达式将失败。我们不必在这里转义第一个点,因为它在 [character range]
内,这意味着我们将其称为字符。通常,[character range]
用于列出我们期望在此位置出现的所有字符或类型。当您以非 (^
) 开始 [character range]
时,我们告诉正则表达式不应在此位置出现的所有字符和类型。
如果您决定使用正则表达式并需要更多信息,可以找到它 here。我上面的小入门书可能是所有关于它的知识的 15%。明白了这么多,剩下的学习起来就很简单了。
旁白:
如果我必须做你正在做的事情,我不会删除任何图像。我会将它们全部移动到一个带有日志的目录中,该日志记录了每个文件的来源。然后你可以确保它的 none 是你真正想要保留的东西。一旦您审核了所有图像并且确信整个目录都是垃圾,您就可以手动删除整个目录。换句话说,您的方式假定没有一张图片实际上是界面的一部分,并且根据查看它的设备进行引用。
首先,如果您正在 Linux 工作,解决这个问题的明显方法是使用 bash 文件:
# cleanup.sh
rm path/*-150x150.jpg
rm path/*-100x100.jpg
rm path/*-75x75.jpg
rm path/*-50x50.jpg
只需 运行 这个脚本,您就完成了。
如果您坚持使用Python,那么这个解决方案是对bash方法的翻译:
import os
dir_name = "path"
to_be_deleted = [
"*-150x150.jpg",
"*-100x100.jpg",
"*-75x75.jpeg",
"*-50x50.jpeg",
]
for wildcard in to_be_deleted:
os.system(f"rm {dir_name}/{wildcard}")
更新
这个 bash 文件更短:
rm path/*-*x*.{jpg,jpeg}
更新 2
如果在 Windows 下,您可能没有 rm
命令,因此 Python 解决方案是使用 glob
库:
import glob
import os
dir_name = "path"
to_be_deleted = [
"*-150x150.jpg",
"*-100x100.jpg",
"*-75x75.jpeg",
"*-50x50.jpeg",
]
for wildcard in to_be_deleted:
for path in glob.glob(f"{dir_name}/{wildcard}"):
os.remove(path)
我目前正在尝试从网络服务器上清理一些媒体文件夹。问题是每个文件都以多种不同的分辨率复制,而且并非所有都相同。
例如:picture1.jpg
也有 picture1-150x150.jpg
、picture1-100x100.jpg
和 picture1-50x50.jpg
。
虽然其中很多是相同的,但也有很多是不同的。
所以我首先尝试了这个:
import os
dir_name = "path"
test = os.listdir(dir_name)
for item in test:
if item.endswith("150x150.jpg"):
os.remove(os.path.join(dir_name, item))
它完成了它的工作,但在添加各种不同的分辨率和文件扩展名(jpg、jpeg、png、etcpp)后变得非常臃肿:
if item.endswith("-150x150.jpg"):
os.remove(os.path.join(dir_name, item))
if item.endswith("-100x100.jpg"):
os.remove(os.path.join(dir_name, item))
if item.endswith("-75x75.jpeg"):
os.remove(os.path.join(dir_name, item))
if item.endswith("-50x50.jpeg"):
os.remove(os.path.join(dir_name, item))
etc...
所以我尝试将这些决议输入文本文件并将其用作列表。
import os
dir_name = "path"
folder = os.listdir(dir_name)
with open('list.txt') as f:
lines = f.read().splitlines()
for file in folder:
if file.endswith(str(lines)):
os.remove(os.path.join(dir_name, file))
虽然我能够在一定程度上阅读和修改代码,但这是我在 Google 半天后设法做到的。 因此,我恳请任何帮助或指导。
我认为您需要检查行列表
的所有元素然后,如果文件名中出现列表行的元素,则将其删除
for file in folder:
for line in lines:
if file.endswith(str(line)):
os.remove(os.path.join(dir_name, file))
endswith 方法接受一个元组作为参数,这意味着您可以将所有扩展合并到一个变量中。
extensions = ("-150x150.jpg","-100x100.jpg","-75x75.jpeg","-50x50.jpeg")
然后你把这个变量传给endswith
if file.endswith(extensions):
os.remove(os.path.join(dir_name, file))
这是我用于概念验证的片段:
files = [
"file1",
"file2.jpg",
"file123",
"file4.jpg.old",
"file5.txt"
]
extensions = (
".jpg",
".exe",
".txt"
)
for file in files:
if file.endswith(extensions):
print(f'File :{file} should be delete')
else:
print(f'Skipping:{file}')
返回:
╰─ python3 app.py
Skipping:file1
File :file2.jpg should be delete
Skipping:file123
Skipping:file4.jpg.old
File :file5.txt should be delete
除了“-150x150.jpg”之外,是否有任何文件名中包含破折号?如果没有,您可以执行以下操作:
import os
dir_name = "path"
folder = os.listdir(dir_name)
for file in folder:
split_file_name = file.split('-')
if len(split_file_name) > 1:
os.remove(os.path.join(dir_name, file))
如果您不能保证只有一个破折号,那么我认为正则表达式将是您最好的选择。
import os
import re
dir_name = "path"
folder = os.listdir(dir_name)
pattern = re.compile('[a-zA-Z0-9_\-]+-\d+x\d+.jpg')
for file in folder:
if pattern.match(file):
os.remove(os.path.join(dir_name, file))
您可以简单地制作一个可以处理所有不同可能性的正则表达式,并使用它来过滤文件名。我使用您提供的循环编写了这个示例。您可以将其更改为循环到收集文件名所需的任何内容。这个例子的重点是正则表达式过滤器。
import re, os
dir_name = "path"
test = os.listdir(dir_name)
fmt = re.compile(r'([\w\d_]+)-\d{1,4}x\d{1,4}\.(jpg|png|jpeg|gif|bmp|tga)', re.I)
for item in test:
if fmt.search(item):
os.remove(os.path.join(dir_name, item))
如果您不理解正则表达式,这里有一个细分:
([\w\d_]+)
获取连续的单词、数字和下划线。 (例如:'my_family_pic1')。 +
表示至少应有 1 个单词、数字或下划线,但要尽可能多地连续出现。 +
的补充是 *
,它将匹配描述数据的 0 次或多次连续出现。
-\d{1,4}x\d{1,4}
获取从“-0x0”到“-9999x9999”的任何组合。 {1,4}
部分只是说应该有 1 到 4 个连续的前面描述的类型的字符。在这种情况下,该类型将是数字。
\.(jpg|png|jpeg|gif|bmp|tga)
这部分的字面意思是我们期望一个点后跟 'jpg' OR 'png' OR 'jpeg' OR... 我们必须转义点,因为正则表达式中的点意味着“任何非空白字符”,除非我们使用 re.S
标志,在这种情况下,点将匹配任何内容。通过转义它,我们告诉正则表达式我们真的只是想找到一个点。 (group)
用于包含一组可能性,隔离逻辑 and/or 隔离一段数据,可以通过其组索引直接引用。如此处所用,您可以将其视为条件语句。如果我们在此处删除分组,则正则表达式将找到 ex:'some_file-10x10.jpg' 或完全失败。遇到ex:'.png'却只找ex:'png',永远匹配不到.
当前的正则表达式只会查找文件名中具有尺寸的图像(即.. -150x150)。如果你想删除任何图片,你可以将正则表达式更改为:
fmt = re.compile(r'([^.]+)\.(jpg|png|jpeg|gif|bmp|tga)', re.I)
这将从接受每个不是(^
)点的字符开始,然后是点和扩展名。这相当于说“我们不关心开始,只要确保它以某种方式结束”。但是,如果实际文件名中有任何点,则此表达式将失败。我们不必在这里转义第一个点,因为它在 [character range]
内,这意味着我们将其称为字符。通常,[character range]
用于列出我们期望在此位置出现的所有字符或类型。当您以非 (^
) 开始 [character range]
时,我们告诉正则表达式不应在此位置出现的所有字符和类型。
如果您决定使用正则表达式并需要更多信息,可以找到它 here。我上面的小入门书可能是所有关于它的知识的 15%。明白了这么多,剩下的学习起来就很简单了。
旁白:
如果我必须做你正在做的事情,我不会删除任何图像。我会将它们全部移动到一个带有日志的目录中,该日志记录了每个文件的来源。然后你可以确保它的 none 是你真正想要保留的东西。一旦您审核了所有图像并且确信整个目录都是垃圾,您就可以手动删除整个目录。换句话说,您的方式假定没有一张图片实际上是界面的一部分,并且根据查看它的设备进行引用。
首先,如果您正在 Linux 工作,解决这个问题的明显方法是使用 bash 文件:
# cleanup.sh
rm path/*-150x150.jpg
rm path/*-100x100.jpg
rm path/*-75x75.jpg
rm path/*-50x50.jpg
只需 运行 这个脚本,您就完成了。
如果您坚持使用Python,那么这个解决方案是对bash方法的翻译:
import os
dir_name = "path"
to_be_deleted = [
"*-150x150.jpg",
"*-100x100.jpg",
"*-75x75.jpeg",
"*-50x50.jpeg",
]
for wildcard in to_be_deleted:
os.system(f"rm {dir_name}/{wildcard}")
更新
这个 bash 文件更短:
rm path/*-*x*.{jpg,jpeg}
更新 2
如果在 Windows 下,您可能没有 rm
命令,因此 Python 解决方案是使用 glob
库:
import glob
import os
dir_name = "path"
to_be_deleted = [
"*-150x150.jpg",
"*-100x100.jpg",
"*-75x75.jpeg",
"*-50x50.jpeg",
]
for wildcard in to_be_deleted:
for path in glob.glob(f"{dir_name}/{wildcard}"):
os.remove(path)