Переименование нескольких файлов в каталоге в Python

Я пытаюсь переименовать некоторые файлы в каталоге с помощью Python.

Скажем, у меня есть файл с именем CHEESE_CHEESE_TYPE.*** и вы хотите удалить CHEESE_, поэтому мое результирующее имя файла будет CHEESE_TYPE

Я пытаюсь использовать os.path.split, но он работает неправильно. Я также рассматривал использование строковых манипуляций, но также не имел успеха.

Ответ 1

Используйте os.rename(src, dst), чтобы переименовать или переместить файл или каталог.

$ ls
cheese_cheese_type.bar  cheese_cheese_type.foo
$ python
>>> import os
>>> for filename in os.listdir("."):
...  if filename.startswith("cheese_"):
...    os.rename(filename, filename[7:])
... 
>>> 
$ ls
cheese_type.bar  cheese_type.foo

Ответ 2

Здесь script на основе вашего последнего комментария.

#!/usr/bin/env python
from os import rename, listdir

badprefix = "cheese_"
fnames = listdir('.')

for fname in fnames:
    if fname.startswith(badprefix*2):
        rename(fname, fname.replace(badprefix, '', 1))

Ответ 3

Предполагая, что вы уже находитесь в каталоге и что "первые 8 символов" из вашего комментария всегда остаются истинными. (Хотя "CHEESE_" - 7 символов...? Если это так, измените 8 ниже на 7)

from glob import glob
from os import rename
for fname in glob('*.prj'):
    rename(fname, fname[8:])

Ответ 4

Следующий код должен работать. Он принимает каждое имя файла в текущем каталоге, если имя файла содержит шаблон CHEESE_CHEESE_, после чего оно переименовывается. Если ничего не сделано для имени файла.

import os
for fileName in os.listdir("."):
    os.rename(fileName, fileName.replace("CHEESE_CHEESE_", "CHEESE_"))

Ответ 5

У меня такая же проблема, когда я хочу заменить пробел в любом PDF файле на тире -. Но файлы были в нескольких подкаталогах. Поэтому мне пришлось использовать os.walk(). В вашем случае для нескольких подкаталогов это может быть примерно так:

import os
for dpath, dnames, fnames in os.walk('/path/to/directory'):
    for f in fnames:
        os.chdir(dpath)
        if f.startswith('cheese_'):
            os.rename(f, f.replace('cheese_', ''))

Ответ 6

Попробуйте следующее:

import os
import shutil

for file in os.listdir(dirpath):
    newfile = os.path.join(dirpath, file.split("_",1)[1])
    shutil.move(os.path.join(dirpath,file),newfile)

Я предполагаю, что вы не хотите удалять расширение файла, но вы можете просто сделать тот же раскол с периодами.

Ответ 7

Этот материал отлично подходит для IPython, который имеет интеграцию с оболочкой.

In [1] files = !ls
In [2] for f in files:
           newname = process_filename(f)
           mv $f $newname

Примечание. Чтобы сохранить это в script, используйте расширение .ipy и префикс всех команд оболочки с помощью !.

Смотрите также: http://ipython.org/ipython-doc/stable/interactive/shell.html

Ответ 8

Кажется, что ваша проблема связана скорее с определением нового имени файла, а не с самим переименованием (для которого вы можете использовать метод os.rename).

Из вашего вопроса неясно, какой шаблон вы хотите переименовать. Нет ничего плохого в строковых манипуляциях. Регулярное выражение может быть тем, что вам нужно здесь.

Ответ 9

Эта команда удалит исходную строку "CHEESE_" из всех файлов в текущем каталоге, используя renamer:

$ renamer --find "/^CHEESE_/" *

Ответ 10

Вот более общее решение:

Этот код может быть использован для удаления любого конкретного символа или набора символов рекурсивно из всех имен файлов в каталоге и заменяет их любым другим символом, набором символов или символом.

import os

paths = (os.path.join(root, filename)
        for root, _, filenames in os.walk('C:\FolderName')
        for filename in filenames)

for path in paths:
    # the '#' in the example below will be replaced by the '-' in the filenames in the directory
    newname = path.replace('#', '-')
    if newname != path:
        os.rename(path, newname)

Ответ 11

Вы можете использовать функцию os.system для простоты и вызвать bash для выполнения задачи:

import os
os.system('mv old_filename new_filename')

Ответ 12

Первоначально я искал какой-то графический интерфейс, который позволял бы переименовывать с использованием регулярных выражений и который имел предварительный просмотр результата перед применением изменений.

В Linux я успешно использовал krename, в Windows Total Commander переименование с помощью регулярных выражений, но я не нашел достойного бесплатного эквивалента для OSX, поэтому я написал питон script, который работает рекурсивно и по умолчанию печатает только имена новых файлов без каких-либо изменений. Добавьте переключатель '-w', чтобы фактически изменить имена файлов.

#!/usr/bin/python
# -*- coding: utf-8 -*-

import os
import fnmatch
import sys
import shutil
import re


def usage():
    print """
Usage:
        %s <work_dir> <search_regex> <replace_regex> [-w|--write]

        By default no changes are made, add '-w' or '--write' as last arg to actually rename files
        after you have previewed the result.
        """ % (os.path.basename(sys.argv[0]))


def rename_files(directory, search_pattern, replace_pattern, write_changes=False):

    pattern_old = re.compile(search_pattern)

    for path, dirs, files in os.walk(os.path.abspath(directory)):

        for filename in fnmatch.filter(files, "*.*"):

            if pattern_old.findall(filename):
                new_name = pattern_old.sub(replace_pattern, filename)

                filepath_old = os.path.join(path, filename)
                filepath_new = os.path.join(path, new_name)

                if not filepath_new:
                    print 'Replacement regex {} returns empty value! Skipping'.format(replace_pattern)
                    continue

                print new_name

                if write_changes:
                    shutil.move(filepath_old, filepath_new)
            else:
                print 'Name [{}] does not match search regex [{}]'.format(filename, search_pattern)

if __name__ == '__main__':
    if len(sys.argv) < 4:
        usage()
        sys.exit(-1)

    work_dir = sys.argv[1]
    search_regex = sys.argv[2]
    replace_regex = sys.argv[3]
    write_changes = (len(sys.argv) > 4) and sys.argv[4].lower() in ['--write', '-w']
    rename_files(work_dir, search_regex, replace_regex, write_changes)

Пример использования

Я хочу перевернуть части имени файла следующим образом, т.е. переместить бит m7-08 в начало имени файла:

# Before:
Summary-building-mobile-apps-ionic-framework-angularjs-m7-08.mp4

# After:
m7-08_Summary-building-mobile-apps-ionic-framework-angularjs.mp4

Это приведет к сухому прогону и распечатает новые имена файлов, не переименовав их вообще:

rename_files_regex.py . "([^\.]+?)-(m\\d+-\\d+)" "\\2_\\1"

Это приведет к фактическому переименованию (вы можете использовать либо -w, либо --write):

rename_files_regex.py . "([^\.]+?)-(m\\d+-\\d+)" "\\2_\\1" --write

Ответ 13

import os строка импорта def rename_files():

#List all files in the directory
file_list = os.listdir("/Users/tedfuller/Desktop/prank/")
print(file_list)

#Change current working directory and print out it location
working_location = os.chdir("/Users/tedfuller/Desktop/prank/")
working_location = os.getcwd()
print(working_location)

#Rename all the files in that directory
for file_name in file_list:
    os.rename(file_name, file_name.translate(str.maketrans("","",string.digits)))

rename_files()

Ответ 14

Как насчет этого:

import re
p = re.compile(r'_')
p.split(filename, 1) #where filename is CHEESE_CHEESE_TYPE.***

Ответ 15

Это работает для меня.

import os
for afile in os.listdir('.'):
    filename, file_extension = os.path.splitext(afile)
    if not file_extension == '.xyz':
        os.rename(afile, filename + '.abc')