Эквивалент Python для поиска -exec
Я пытаюсь запустить эту команду BASH в Попене:
find /tmp/mount -type f -name "*.rpmsave" -exec rm -f {} \;
Но каждый раз, когда я получаю: "find: отсутствует аргумент`-exec'\n"в stderr.
Каким будет Python-эквивалент этого?
Мой наивный подход был бы:
for (root,files,subdirs) in os.walk('/tmp/mount'):
for file in files:
if '.rpmsave' in file:
os.remove(file)
наверняка есть лучший, более питонный способ сделать это?
3 ответа
У вас есть два вопроса здесь - во-первых, почему ваш Popen
строительство не работает, а во-вторых, как использовать os.walk
должным образом. Нед ответил на второй, поэтому я расскажу на первый: вы должны знать, что оболочка может сбежать. \;
сбежал ;
так как обычно ;
будет интерпретирован Bash как разделяющий две команды оболочки, и не будет передан find
, (В некоторых других оболочках {}
также должен быть экранирован.)
Но с Popen
вы вообще не хотите использовать оболочку, если можете ее избежать. Итак, это должно работать:
import subprocess
subprocess.Popen(('find', '/tmp/mount', '-type', 'f',
'-name', '*.rpmsave', '-exec', 'rm', '-f', '{}', ';'))
То, что у вас есть, это в основном способ сделать это. У вас есть три разные вещи, которые вы координируете: 1) ходить по дереву, 2) работать только с файлами.rpmsave и 3) удалять эти файлы. Где бы вы нашли что-то, что изначально делает все это, не объясняя это? Команда Bash и код Python имеют примерно одинаковую сложность, что неудивительно.
Но вы должны исправить свой код, например так:
for root,files,subdirs in os.walk('/tmp/mount'):
for file in files:
if file.endswith('.rpmsave'):
os.remove(os.path.join(root, file))
Если вы обнаружите, что делаете это много. Это может быть полезной оболочкой для os.walk:
def files(dir):
# note you have subdirs and files flipped in your code
for root,subdirs,files in os.walk(dir):
for file in files:
yield os.path.join(root,file)
Чтобы удалить группу файлов с определенным расширением внутри каталога:
[os.remove(file) for file in files(directory) if file.endswith('.extension')]