Найти - Пользователи
Полная версия: Нужно заархивировать
Начало » Python для новичков » Нужно заархивировать
1
stepan.puzan31
Доброго времени суток.
Приступил к изучению Пайтона и есть трудности.
В общем есть задача.
Существует директория /root/test/ в ней некое количество файлов размером от 100Кб (примерно) до 28Мб (опять таки примерно). А теперь собственно сама задача: необходимо сортивать эти файлы по директориям и заархивить таким образом, чтобы каждая заархивированная директория не превышала 50 Мб.
Все мои попытки были тщетны, к примеру если наполню директорию до 48 Мб, а следующий файл будет 3Мб, то цикл конечно же остановится, но на 51 Мб в итоге, что выходит за рамки моей задачи.
doza_and
Так вы без питона своими словами изложите алгоритм который хотите реализовать.

А вообще архиваторы умеют бить архивы на куски заданного размера, надо просто ключи правильно задать :)
py.user.next
stepan.puzan31
В общем есть задача.
Довольно сложная задача для новичка. Её делать-то надо на shell'е, а на питоне она ещё сложнее, чем на shell'е, делается, так как он для таких действий не очень заточен, в отличие от shell'а.

По крайней мере я бы на питоне это делать не стал, хотя владею и shell'ом, и питоном одинаково, так как на питоне это будет муторнее раза в три. Хотя для тренировки самих навыков в питоне можно и написать, если задачка именно учебная.
stepan.puzan31
А вообще архиваторы умеют бить архивы
Каждый архив должен иметь возможность использования без других)


Её делать-то надо на shell'е, а на питоне она ещё сложнее
По Пайтону я хотябы книжку открывал, и некоторые файловые манипуляции на нем уже реализованы. Но вот тут пока не ясо что делать.
Но все равно, спасибо.
scidam
Алгоритм видится мне следущий:

0. Исходим из предположения, что размер архива данной папки не превосходит ее исходного размера (т.е. архивация не увеличивает занимаемого объема)

1. Создаем массив кортежей т.е. пути к файлам и размеры файлов соответственно (это можно сделать при помощи os модуля)

2. сортируем данный массив по размеру файлов, допустим по возрастанию (как-нибудь так: x=sorted(x, key=lambda x: x))

3. дальше создаем цикл типа while пока текущий массив кортежей непуст, а внутри него другой цикл, который последовательно от большего к меньшему пробует добавить каждый файл, пока размер контейнера меньше 50 МБ:

 files_array= [('path/to/file', file_size), ....] # sort it first... 
containers = []
while files_array:
    container = []
    pendings = []
    for k in reversed(range(len(files_array))):
          container.append(files_array[k])
          pendings.append(k)
          if sum(map(lambda x: x[1], container)) >= 50:
              container.pop()
              pendings.pop()
    containers.append(container)
    for i in pendings:
         del files_array[i] # удаляем тех,  кто в списке не удаление

В результате, получим оптимальный массив контейнеров – каждый из которых не превосходит 50 МБ. Далее, в соответствии с файлами в контейнерах, можно сформировать директории и их упаковать.



FishHook
scidam

Зачем такие многоэтажные конструкции?
     for k in reversed(range(len(files_array))):
          container.append(files_array[k])

Достаточно же просто
 for k in reversed(files_array):
          container.append(k)
scidam
FishHook
Да, согласен, можно упростить. Тогда и pendings не нужен будет, достаточно будет удалить элементы, которые в текущем контейнере.

stepan.puzan31
Большое спасибо за помощь)
This is a "lo-fi" version of our main content. To view the full version with more information, formatting and images, please click here.
Powered by DjangoBB