使用正则表达式从目录中删除特定文件名的文件

4

我正在尝试创建一个代码,根据掩码删除文件夹中的文件。所有包含17的文件都应该被删除。文件名格式为??_????17*.*,其中?代表任何1..n,A..z, _和17 - 在任何文件中(其他文件也包含18),其扩展名并不重要。例如:AB_DEFG17Something.Anything - Copy (2).txt

import os
import re

dir_name = "/Python/Test_folder"         # open the folder and read files
testfolder = os.listdir(dir_name)

def matching(r, s):                      # condition if there's nothing to match
match = re.search(r, s)
if match:
return match.group()
return "Files don't exist!"

matching(r'^\w\w\[_]\w\w\w\w\[1]\[7]\w+\[.]\w+', testfolder)  # matching the file's mask

for item in testfolder.index(matching):
if item.name(matching, s):
os.remove(os.path.join(dir_name, item))

# format of filenames not converted :  ??_????17*.* 
# convert for python separarately   :  [\w][\w][_\w][\w][\w][\w]\[1]\[7][\w]+[\.][\w]+
# ? - Any symbol 1..n,A..z \w repeating is * 
# * - Any number of symbols 1..n, A..z
# _ and 17 - in any files `

还有一些错误。

文件"D:\Python\Test_folder\Remover v2.py"的第14行,匹配(r'\w\w[_]\w\w\w\w[1][7]\w+[.]\w+', testfolder) # 匹配文件掩码  文件"D:\Python\Test_folder\Remover v2.py"的第9行,在matching函数中 match = re.search(r, s) 文件"c:\Program Files (x86)\Wing IDE Personal 6.0\bin\runtime-python2.7\Lib\re.py"的第146行,使用search方法 return _compile(pattern, flags).search(string)

我是一名初学者,采用业余的方式想要获得PY方面的经验,并且通过并行学习来了解细节。我做错了什么?任何帮助都是有用的。谢谢。

Shell已经支持通配符删除文件。你的正则表达式似乎与你的问题陈述中的glob通配符没有特别密切的对应关系。在这里,Python的“glob”模块可能是更好的选择。 - tripleee
对于Python问题,您必须确保缩进正确。让我们猜测哪些错误是您代码中的实际错误,而不是由于粗心的复制/粘贴引起的问题,这是浪费大家时间的行为。尝试将您的代码作为单个块粘贴,然后使用鼠标选择该块,并键入ctrl-k以将其缩进为代码。(在此网站的移动版本中似乎无法使用此功能)。另请参见帮助 - tripleee
“1”,“7”和“_”只是匹配它们自己,没有必要将它们放在字符类中。你尝试中的“[`前面的反斜杠将其变成了一个不是字符类。 - tripleee
matching 函数在没有匹配的情况下返回一个字符串似乎是一个特别糟糕的选择。如果您真的认为这需要作为一个单独的函数存在,那么请让它返回一些易于在其他代码中处理的内容,比如 NoneFalse,并且只在直接与用户交流时使用人性化的表达方式。 - tripleee
4个回答

8
不要重复造轮子,而是使用 glob() 函数代替:
import os
from glob import glob

for file in glob('/Python/Test_folder/AB_CDEF17*.*'):
    os.remove(file)

2
使用 glob.glob
for filename in glob.glob(os.path.join(dirname, "AB_CDEF17*.*")):
    try:
        # Trying to remove a current file
        os.remove(os.path.join(dirname, filename))
    except EnvironmentError:
        # You don't have permission to do it
        pass

使用 os.scandirre.match
pattern = re.compile(r"AB_CDEF17\w+\.\w+")
for filename in os.scandir(dirname):
    if pattern.match(filename):
        try:
            os.remove(os.path.join(dirname, filename))
        except EnvironmentError:
            pass

1
您可以直接从命令行使用以下命令:
cd $PATH; for inode in $(ls -il AB_CDEF17*.* | awk '{print $1}'); do find . -type f -inum $inode -exec rm -i {} \;; done
  • cd $PATH; 进入指定的文件夹
  • $(ls -il AB_CDEF17*.* | awk '{print $1}') 将当前目录中所有文件的i节点号打印出来,我使用这个方法因为文件名中似乎有空格,所以rm命令无法正常工作。
  • find . -type f -inum $inode -exec rm -i {} \;; 根据i节点号查找文件并通过询问您的许可删除它们。

如果您对自己的操作非常确定,并且确实想在某些Python代码中嵌入它:

from subprocess import call
call('cd $PATH; for inode in $(ls -il AB_CDEF17*.* | awk '{print $1}'); do find . -type f -inum $inode -exec rm -f {} \;; done') 

注意:通过输入rm -f命令,文件将被无需确认删除。


1
你可以尝试使用glob解决方案。
例如,这些是文件夹中的文件。
~/Test-folder$ ls *.txt -1
AB_DEFG17Sitanything.n.txt
AB_DEFG17SOManything.copy(2).txt
AB_DEFG17SOManything.nis.txt
AB_DEFG17SOManything.n.txt
AB_DEFG18SOManything.n.txt
AB_DEFG28SOManything.n.txt
AB_PIZG17SOManything.piz.txt
AB_PIZG28SOManything.n.txt
AB_PIZG76SOManything.n.txt

我的代码

import glob
r = [f for f in glob.glob("*.txt") if "AB_DEFG" in f or "17" in f]
for f in r:
    print (f)

你会得到
AB_DEFG17SOManything.n.txt
AB_DEFG17SOManything.nis.txt
AB_PIZG17SOManything.piz.txt
AB_DEFG17Sitanything.n.txt
AB_DEFG28SOManything.n.txt
AB_DEFG17SOManything.copy(2).txt
AB_DEFG18SOManything.n.txt

我忘记添加删除解决方案。
import glob,os
r = [f for f in glob.glob("*.txt") if "AB_DEFG" in f or "17" in f]
for f in r:
    os.remove(f)

只有两个文件会留下。
AB_PIZG28SOManything.n.txt
AB_PIZG76SOManything.n.txt

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接