В чем разница между a[bc]d
и a{b,c}d
? Почему люди используют, a{b,c}d
когда уже есть a[bc]d
?
brace-expansion
pattern-matching
Вейцзюнь Чжоу
источник
источник
command a[bc]d
?ls
и вы когда-нибудь попробуете только отдельные символы, они будут работать одинаково.Ответы:
Два совершенно разные.
a[bc]d
это шаблон файла (в оболочках, кромеfish
). Он расширится до двух имен файловabd
и,acd
если это имена существующих файлов в текущем каталоге.[...]
Часть представляет собой квадратные скобки выражение , которое соответствует одному символу из перечисленных (или элементы которых объединяются , когда диапазоны включены). Чтобы соответствовать шаблонуa[bc]d
, символ между строкамиa
иd
именем файла должен быть либо a,b
либо ac
.Если
abd
существует, ноacd
не существует, то он будет только расширятьсяabd
, и наоборот.Если ни один
abd
, ниacd
существовать, в зависимости от оболочки и вариант, это вызовет ошибку (оригинал Unixsh
,(t)csh
,zsh
,fish
,bash -O failglob
) и , возможно , выйти из оболочки, или оставить шаблон unexpanded¹ (Bourne-подобные иrc
-как оболочки) или расширяться ничего (bash/zsh/yash -o nullglob
некоторые старые версииfish
Unix,sh
и(t)csh
если в той же команде есть другие совпадающие глобусы).a{b,c}d
это расширение скобки (в оболочках, которые их поддерживают). Это расширится до двух строкabd
иacd
.{...}
Часть представляет собой разделенные запятые набора строк (в данном примере, в некоторой оболочке, он также может представлять собой диапазон , такие какa..k
или20..25
или более продвинутых из них , как00..20..2
и0..20..2%02d
), а также расширение вычисляется путем объединения каждого из этих строк с фланкирующим струныa
иd
. Эти строки могут быть длиннее одного символа и также могут быть расширениями скобок.Расширение происходит независимо от того, соответствуют ли эти строки существующим именам файлов или нет.
Если вы строите строки, используйте расширение скобки. Если вы соответствуете именам файлов, используйте шаблон имени файла.
¹ В данном конкретном случае
a[bc]d
может оказаться имя существующего файла, поэтому использование таких вещей, какrm -f ./*.[ch]
в этих оболочках , потенциально опасно иrm -f ./*.{c,h}
представляет меньшую проблему.источник
a{b,c}d
, что в ,b
иc
части не должны быть отдельными буквами; напримерex{ten,ci}sion
. Хотяex[tenci]sion
или что-то будет соответствовать только одной из этих букв.a[bc]d
является сопоставлением с образцом и является частью стандарта POSIX. В POSIX это вводится как «выражение скобки образца». Это задокументировано в разделе 2.13 руководстваВ разделе 2.13.3 также упоминается то, что он ведет себя не так, как можно ожидать от обычных регулярных выражений, когда он используется для расширения имени файла (выделено мной).
a{b,c}d
это расширение скобок , это не в спецификации POSIX. Вот соответствующая часть из Баш руководства (выделено мной):Согласно комментарию @mosvy, это впервые появилось из,
csh
но поведение вbash
отличается отcsh
других оболочек. Этот тип расширения фигурных скобок также присутствует вglob(3)
.Существует еще один тип расширения фигурных скобок,
{a..z}
который появился только послеbash
3.0, а вbash
4.0 добавлено больше .В оболочке, где включено глобирование, выполнить в пустой папке, возвращается следующий результат
В ответ на комментарий @ Jesse_b, если вы работаете в интерактивной оболочке и оба они применимы,
a[bc]d
набрать текст будет меньше проблем. Напримерgrep pattern [ab][12].txt
.источник
csh
, задолго доbash
. Он также присутствует в библиотечной функции glob (3). Разница в том, чтоbash
он выполняется до других расширений:a=A; ab=A/B; ac=A/C; echo $a{b,c}
будет работать в bash иначе, чем любая другая оболочка.