2

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

После небольшого поиска я нашел, а затем изменил некоторые вещи для создания этой команды:

find . -name "z*.jpg" -exec cp '{}' ~/Extracted/ \;

Это, казалось бы, сработало, однако я обнаружил, что изображения с одинаковыми именами будут перезаписаны, поэтому я сделал это:

find . -name "z*.jpg" -exec cp -n '{}' ~/Extracted/ \;

Но теперь изображения с таким же именем просто игнорируются.

Можно ли как-нибудь это сделать, чтобы каждое изображение копировалось, а изображения с одинаковыми именами переименовывались?

2 ответа2

4

GNU cp(1) имеет опцию резервного копирования:

cp --backup SOURCE [SOURCE...] [DESTINATION]

Это имеет следующие эффекты, которыми можно управлять с помощью других опций, как описано на странице руководства cp(1):

--backup[=CONTROL]
          make a backup of each existing destination file

-b     like --backup but does not accept an argument

-S, --suffix=SUFFIX
          override the usual backup suffix

Суффикс резервной копии равен ~ , если он не установлен с параметром --suffix или SIMPLE_BACKUP_SUFFIX . Метод управления версиями можно выбрать с помощью параметра --backup или переменной среды VERSION_CONTROL . Вот значения:

  • none , off: никогда не создавать резервные копии (даже если --backup )
  • numbered , t: сделать пронумерованные резервные копии
  • existing , nil: пронумерованы, если существуют пронумерованные резервные копии, в противном случае просто
  • simple , never: всегда делайте простые резервные копии

пример

cp --backup=existing --suffix=.orig ~/Music/* ~/Videos

Это скопирует все файлы в ~/Music в ~/Videos . Если файл с тем же именем существует в месте назначения, он переименовывается путем добавления .orig к его имени в качестве резервной копии. Если существует файл с тем же именем, что и у резервной копии, резервная копия вместо этого переименовывается, добавляя .1 и, если он также существует, .2 и т.д. Только после этого исходный файл копируется в место назначения.

Если вы хотите копировать файлы в подкаталогах рекурсивно, используйте -R:

cp -R --backup=existing --suffix=.orig ~/Music ~/Videos
2

Ваша проблема на самом деле найти вариант cp который создает целевой файл под другим именем, если он уже существует. Я не знаю инструмент, который делает это, однако, это не трудно реализовать себя:

#!/bin/bash
cp -vn "$1" "$2"/ || cp -vn "$1" "$2"/"${1##*/}"~"$(md5sum "$1" | cut -f1 -d' ')"

Этот сценарий снова вызывает cp в случае сбоя, добавляя контрольную сумму к имени файла. Недостаток: если появляется третий файл с тем же именем, он перезаписывает второй файл, если они идентичны.

Учитывая, что приведенный выше скрипт называется saveCopy и хранится в родительском рабочем каталоге, работает следующее:

$ find . -name 'z*.jpg' -exec ./saveCopy {} /tmp/Extracted/ \;
./a/z1.jpg -> /tmp/Extracted/z1.jpg
./a/z2.jpg -> /tmp/Extracted/z2.jpg
./a/z3.jpg -> /tmp/Extracted/z3.jpg
/tmp/Extracted/z3.jpg not overwritten
./b/z3.jpg -> /tmp/Extracted//z3.jpg~d41d8cd98f00b204e9800998ecf8427e
./b/z4.jpg -> /tmp/Extracted/z4.jpg

Имейте в виду, что скрипт работает только для одного входного файла и если целью является каталог! Это, безусловно, может быть улучшено ;-)

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .