Скопируйте все файлы с определенным расширением из всех подкаталогов
В unix я хочу скопировать все файлы с определенным расширением (все файлы excel) из всех подкаталогов в другой каталог. У меня есть следующая команда:
cp --parents `find -name \*.xls*` /target_directory/
Проблемы с этой командой:
-
Он также копирует структуру каталогов, и мне нужны только файлы (поэтому все файлы должны быть в /target _directory/)
-
Он не копирует файлы с пробелами в имена файлов (которых довольно много)
Любые решения для этих задач?
Ответы
Ответ 1
--parents
копирует структуру каталогов, поэтому вам следует избавиться от этого.
Как вы это написали, выполняется find
, и вывод помещается в командную строку таким образом, что cp
не может различать пробелы, разделяющие имена файлов, и пробелы внутри имени файла. Лучше сделать что-то вроде
$ find . -name \*.xls -exec cp {} newDir \;
в котором cp
выполняется для каждого имени файла, которое find
находит, и правильно передал имя файла. Здесь подробнее об этой технике.
Вместо всего вы можете использовать zsh и просто введите
$ cp **/*.xls target_directory
zsh
может расширять подстановочные знаки, чтобы включать подкаталоги, и делает такие вещи очень легкими.
Ответ 2
Из всего вышесказанного я придумал эту версию.
Эта версия также работает для меня в терминале восстановления Mac.
find ./ -name '*.xsl' -exec cp -prv '{}' '/path/to/targetDir/' ';'
Он будет выглядеть в текущем каталоге и рекурсивно во всех подкаталогах для файлов с расширением xsl. Он скопирует их все в целевой каталог.
Флаги cp:
- p - сохранить атрибуты файла
- r - рекурсивный
- v - verbose (показывает вам, что
копирование)
Ответ 3
У меня была аналогичная проблема. Я решил это, используя:
find dir_name '*.mp3' -exec cp -vuni '{}' "../dest_dir" ";"
'{}'
и ";"
выполняет копию каждого файла.
Ответ 4
Я тоже должен был сделать это сам. Я сделал это через аргумент -parents для cp:
find SOURCEPATH -name filename*.txt -exec cp --parents {} DESTPATH \;
Ответ 5
find [SOURCEPATH] -type f -name '[PATTERN]' |
while read P; do cp --parents "$P" [DEST]; done
Вы можете удалить --parents, но существует риск столкновения, если несколько файлов имеют одно и то же имя.