
Я знаю, что могу использовать подстановочный знак для извлечения файлов с именами определенного формата в bash с помощью звездочки, например так:
$ ls
a01 a02 a03 a04 a05 a06 a07 a08 a09 b01 b02 b03 b04 b05 b06 b07 b08 b09
$ ls a*
a01 a02 a03 a04 a05 a06 a07 a08 a09
$ ls b*
b01 b02 b03 b04 b05 b06 b07 b08 b09
Но если бы я хотел сделать что-то вроде перемещения всех файлов, начинающихся с буквы a, в каталог с именем a
, а все файлы, начинающиеся с буквы b, в каталог с именем b
, как бы я это сделал с помощью одной команды?
Можете ли вы сделать что-то вроде этого:
$ mv *0* */
Но как-то же сослаться на первую звездочку в аргументе о переходе?
решение1
Одна команда, одна строка:
for n in *;do [ -f "$n" ] && case "$n" in a*) mv "$n" a/;; b*) mv "$n" b/;; esac; done
В качестве альтернативы можно было бы вывести имя каталога из имени файла, но я изначально этого не показывал, полагая, что это будет более длинная строка. Например, оператор в цикле будет (первая попытка):
d=$(echo "$n" | sed -e 's/^\(.\).*/\1/'); [ -f "$n" ] && mv "$n" $d/
будет использовать первую букву указанного имени файла для получения имени каталога. Сравните с
[ -f "$n" ] && case "$n" in a*) mv "$n" a/;; *b) mv "$n" b/;; esac
для case-statement. На самом деле не намного длиннее, но сложнее для набора на лету. Поскольку bash
упоминается, можно использовать его синтаксис подстроки, ${parameter:offset:length}
чтобы сократить эту строку:
d=${n:0:1}; [ -f "$n" ] && mv "$n" $d/
или
[ -f "$n" ] && mv "$n" ${n:0:1}/
(Я помню это как расширение bash, и не нашел его вPOSIX).
Что касается самого вопроса о повторном использовании подстановочных знаков: это, по-видимому, относится красширение скобки. Они расширяются до того момента, когда они вам понадобятся. Цитата из документации:
Расширение брекетов выполняетсядолюбые другие расширения и любые символы, характерные для других расширений, сохраняются в результате. Этострого текстовый. Баш делаетнетприменить любую синтаксическую интерпретацию к контексту расширения или тексту между фигурными скобками. Чтобы избежать конфликтов с расширением параметров, строка '${' не считается подходящей для расширения фигурных скобок.