Русский
Русский
English
Статистика
Реклама

Сортируем файлы с помощью Python

Штош. Скорее всего, у многих в папке загрузок собиралась куча разных инсталляторов, архивов и прочих файлов. И вот наступает момент, когда из этой кучи экскрементов нужно найти какой-то файл. Вот я и подумал, почему бы не написать скрипт сортировщика по расширениям файлов на Python?

Пишем код

Для начала импортируем стандартный модуль os для работы с операционной системой. С помощью этого модуля мы будем создавать папки и перемещать файлы.

import os

Создадим переменную для пути папки или диска, в которой мы будем сортировать файлы. В моих любимых окошечках путь к файлу записывается через backslash, который в Python является специальным символом экранирования. Поэтому мы либо пишем 2 бэкслэша, либо добавляем перед строкой букву r, тем самым подавляя экранирование.

main_path = 'd:\\down'# main_path = r'd:\down

Чтобы создать папку, используем метод os.mkdir()

os.mkdir(main_path + '\\aboba')

Создаем много папок

Напишем функцию для создания папок из списка названий. Для каждого названия проверяем существование папки с помощью метода os.path.exists().

# also creates folders from dictionary keysdef create_folders_from_list(folder_path, folder_names):    for folder in folder_names:        if not os.path.exists(f'{folder_path}\\{folder}'):            os.mkdir(f'{folder_path}\\{folder}')

Теперь давайте создадим словарь extensions. Ключи - названия папок. Значения - расширения файлов для каждой отдельной папки.

# key names will be folder names!extensions = {    'video': ['mp4', 'mov', 'avi', 'mkv', 'wmv', '3gp', '3g2', 'mpg', 'mpeg', 'm4v',               'h264', 'flv', 'rm', 'swf', 'vob'],    'data': ['sql', 'sqlite', 'sqlite3', 'csv', 'dat', 'db', 'log', 'mdb', 'sav',              'tar', 'xml'],    'audio': ['mp3', 'wav', 'ogg', 'flac', 'aif', 'mid', 'midi', 'mpa', 'wma', 'wpl',              'cda'],    'image': ['jpg', 'png', 'bmp', 'ai', 'psd', 'ico', 'jpeg', 'ps', 'svg', 'tif',               'tiff'],    'archive': ['zip', 'rar', '7z', 'z', 'gz', 'rpm', 'arj', 'pkg', 'deb'],    'text': ['pdf', 'txt', 'doc', 'docx', 'rtf', 'tex', 'wpd', 'odt'],    '3d': ['stl', 'obj', 'fbx', 'dae', '3ds', 'iges', 'step'],    'presentation': ['pptx', 'ppt', 'pps', 'key', 'odp'],    'spreadsheet': ['xlsx', 'xls', 'xlsm', 'ods'],    'font': ['otf', 'ttf', 'fon', 'fnt'],    'gif': ['gif'],    'exe': ['exe'],    'bat': ['bat'],    'apk': ['apk']}

Передаем в функцию create_folders_from_list() новоиспеченный словарь. Папки создадутся из названий ключей.

Получаем пути подпапок и файлов

Пишем функцию для получения путей подпапок. Для каждого объекта в методе os.scandir() проверяем, является ли он каталогом.

def get_subfolder_paths(folder_path) -> list:    subfolder_paths = [f.path for f in os.scandir(folder_path) if f.is_dir()]    return subfolder_paths

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

Нам нужно взять пути подпапок, разделить по бэкслэшам строку и взять последний элемент.

def get_subfolder_names(folder_path) -> list:    subfolder_paths = get_subfolder_paths(folder_path)    subfolder_names = [f.split('\\')[-1] for f in subfolder_paths]    return subfolder_names

Теперь получим пути всех файлов в папке, скопируем функцию get_subfolder_paths() и добавим в условие генератора not.

def get_file_paths(folder_path) -> list:    file_paths = [f.path for f in os.scandir(folder_path) if not f.is_dir()]    return file_paths

Для полного счастья не хватает только функции получения имен файлов.

def get_file_names(folder_path) -> list:    file_paths = [f.path for f in os.scandir(folder_path) if not f.is_dir()]    file_names = [f.split('\\')[-1] for f in file_paths]    return file_names

Сортируем файлы

Приступаем к функции сортировки. Получаем пути файлов в переменную file_paths. Создаем переменную ext_list со списком метода словаря extensions.items(). Обращение к списку по индексу возвращает нам пару ключ-значение в виде списка, первый элемент которого - это ключ или название папки в нашем проекте, а второй элемент - это значение, то есть расширения файлов для этой папки.

def sort_files(folder_path):    file_paths = get_file_paths(folder_path)    ext_list = list(extensions.items())

Теперь создадим цикл для каждого пути файла в списке. Вытащим отдельно расширение и имя файла.

for file_path in file_paths:  extension = file_path.split('.')[-1]  file_name = file_path.split('\\')[-1]

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

for dict_key_int in range(len(ext_list)):  if extension in ext_list[dict_key_int][1]:    print(f'Moving {file_name} in {ext_list[dict_key_int][0]} folder\n')    os.rename(file_path, f'{main_path}\\{ext_list[dict_key_int][0]}\\{file_name}')

Сделать это можно при помощи изменения пути файла методом os.rename("Путь файла сейчас", "Будущий путь файла")

Готовая функция сортировки файлов:

def sort_files(folder_path):    file_paths = get_file_paths(folder_path)    ext_list = list(extensions.items())    for file_path in file_paths:        extension = file_path.split('.')[-1]        file_name = file_path.split('\\')[-1]        for dict_key_int in range(len(ext_list)):            if extension in ext_list[dict_key_int][1]:                print(f'Moving {file_name} in {ext_list[dict_key_int][0]} folder\n')                os.rename(file_path, f'{main_path}\\{ext_list[dict_key_int][0]}\\{file_name}')

Удаляем пустые папки

Остался последний штрих - удаление пустых папок. Все просто. Создаем функцию. Получаем пути подпапок. Проверяем, какой список возвращает метод os.listdir("folder_path") для каждой подпапки. Если возвращается пустой список, значит удаляем папку с помощью os.rmdir("folder_path")

def remove_empty_folders(folder_path):    subfolder_paths = get_subfolder_paths(folder_path)    for p in subfolder_paths:        if not os.listdir(p):            print('Deleting empty folder:', p.split('\\')[-1], '\n')            os.rmdir(p)

Полный код программы

import osmain_path = 'd:\\down'# key names will be folder names!extensions = {    'video': ['mp4', 'mov', 'avi', 'mkv', 'wmv', '3gp', '3g2', 'mpg', 'mpeg', 'm4v', 'h264', 'flv',              'rm', 'swf', 'vob'],    'data': ['sql', 'sqlite', 'sqlite3', 'csv', 'dat', 'db', 'log', 'mdb', 'sav', 'tar', 'xml'],    'audio': ['mp3', 'wav', 'ogg', 'flac', 'aif', 'mid', 'midi', 'mpa', 'wma', 'wpl', 'cda'],    'image': ['jpg', 'png', 'bmp', 'ai', 'psd', 'ico', 'jpeg', 'ps', 'svg', 'tif', 'tiff'],    'archive': ['zip', 'rar', '7z', 'z', 'gz', 'rpm', 'arj', 'pkg', 'deb'],    'text': ['pdf', 'txt', 'doc', 'docx', 'rtf', 'tex', 'wpd', 'odt'],    '3d': ['stl', 'obj', 'fbx', 'dae', '3ds', 'iges', 'step'],    'presentation': ['pptx', 'ppt', 'pps', 'key', 'odp'],    'spreadsheet': ['xlsx', 'xls', 'xlsm', 'ods'],    'font': ['otf', 'ttf', 'fon', 'fnt'],    'gif': ['gif'],    'exe': ['exe'],    'bat': ['bat'],    'apk': ['apk']}# also creates folders from dictionary keysdef create_folders_from_list(folder_path, folder_names):    for folder in folder_names:        if not os.path.exists(f'{folder_path}\\{folder}'):            os.mkdir(f'{folder_path}\\{folder}')def get_subfolder_paths(folder_path) -> list:    subfolder_paths = [f.path for f in os.scandir(folder_path) if f.is_dir()]    return subfolder_pathsdef get_file_paths(folder_path) -> list:    file_paths = [f.path for f in os.scandir(folder_path) if not f.is_dir()]    return file_pathsdef sort_files(folder_path):    file_paths = get_file_paths(folder_path)    ext_list = list(extensions.items())    for file_path in file_paths:        extension = file_path.split('.')[-1]        file_name = file_path.split('\\')[-1]        for dict_key_int in range(len(ext_list)):            if extension in ext_list[dict_key_int][1]:                print(f'Moving {file_name} in {ext_list[dict_key_int][0]} folder\n')                os.rename(file_path, f'{main_path}\\{ext_list[dict_key_int][0]}\\{file_name}')def remove_empty_folders(folder_path):    subfolder_paths = get_subfolder_paths(folder_path)    for p in subfolder_paths:        if not os.listdir(p):            print('Deleting empty folder:', p.split('\\')[-1], '\n')            os.rmdir(p)if __name__ == "__main__":    create_folders_from_list(main_path, extensions)    sort_files(main_path)    remove_empty_folders(main_path)

Настройка программы под свои нужды

Как вы уже могли понять, программа довольно гибкая, и вы можете настроить ее под себя. Для этого нужно всего-лишь изменить словарь extensions.

Приведу пример. Для каждого видео на свой YouTube канал я создаю каталог, в котором есть папки для футажей, картинок, звука, mkv файлов для последующего конвертирования в mp4 (premiere не любит mkv) и самого проекта.

Вот такой словарь.

main_folder = 'f:\\shtosh python\\new video'# key names will be folder names!extensions = {    'img': ['jpg', 'png', 'bmp', 'gif', 'ico', 'jpeg'],    'audio': ['mp3', 'wav'],    'footage': ['mp4', 'mov', 'avi'],    'mkv': ['mkv'],    'prj': []}

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

Заключение

Штош. Код лежит на GitHub. Берите, изменяйте под себя, пользуйтесь на здоровье. Буду рад любому фидбеку.

Источник: habr.com
К списку статей
Опубликовано: 11.06.2021 16:11:37
0

Сейчас читают

Комментариев (0)
Имя
Электронная почта

Python

Пайтон

Питон

Файлы в папке

Файлы

Категории

Последние комментарии

© 2006-2022, personeltest.ru