Предположим, у меня есть следующие папки:
$ ls
css-tricks/ django-tutorial/ good-tuts.txt js-tut/ tutorials/ tuts.txt
Некоторые из них имеют tut
в своих именах. Я хотел бы переместить все файлы/папки, которые имеют tut
в своих именах, в папку tutorials/
. Если я выполню команду
$ mv *tut* tutorials/
Я получаю следующее сообщение:
mv: cannot move 'tutorials' to a subdirectory of itself, 'tutorials/tutorials'
Что я могу сделать, чтобы избежать подобного сценария?
Один из трюков, который я могу придумать, это временно переименовать папку назначения во что-то другое, а после выполнения команды изменить ее обратно на желаемое имя. Однако я надеюсь узнать более элегантное решение проблемы.
решение1
Лично я, в ситуации, когда я собираюсь дать команду интерактивно, просто сделаю это mv *tut* tutorials
и ожидаю получить ошибку "cannot move". Это безвредно, и другие файлы и каталоги будут перемещены, как и ожидалось.
Статус завершения команды будет ненулевым, что будет означать ошибку, но поскольку от него ничего не зависит, его можно проигнорировать.
В этом случае другие имена содержат тире перед tut
:
mv *-tut* tutorials
Или, если у вас есть подобные вещи, python_tut
которые вы хотите переместить, также разрешите подчеркивание:
mv *[_-]tut* tutorials
Или, чтобы потребовать любой дополнительный символ перед подстрокой tut
(которого tutorials
нет),
mv *?tut* tutorials
Немного больше набрав текста и подумав, можно использовать расширенный шаблон подстановки в bash
:
shopt -s extglob
mv *tut!(orials*) tutorials
Этот второй вариант будет соответствовать всему, что содержит подстроку, tut
за которой не следует строка orials
. Шаблон не будет соответствовать tutorials
и также будет пропускаться tutorials1
и т. д.
решение2
Вы также можете использовать find
:
find . -type d -name "*tut*" -not -path "./tutorials" -exec mv -t "tutorials" {} +
решение3
Я получаю следующее сообщение:
mv: cannot move 'tutorials' to a subdirectory of itself, 'tutorials/tutorials'
Просто проигнорируйте ошибку.
Нет, правда. Вы знаете, что получите ошибку, так как шаблон glob совпадает с целью. Вы также знаете, что это ничего не значит, так как система не может переместить каталог внутрь себя, и она достаточно умна, чтобы понять это до того, как испортить вашу файловую систему.
решение4
Самый простой способ — переименовать целевой каталог tutorials/
во что-то другое, не соответствующее расширению имени файла, и переименовать его по своему усмотрению после выполнения перемещения.