zsh: исключение файлов из шаблона

18

Скажем, у меня есть следующие файлы:

|-- bar
`-- foo
    |-- type_A_1
    |-- type_A_2
    |-- type_B_1
    |-- type_B_2
    |-- type_B_xx
    |-- type_B_xx
    `-- something_else

Я думал, что следующая команда

print -l foo/*~{type_B*}

будет печатать все под, foo кроме вещей, которые начинаются с, type_Bно это не так, вместо этого он печатает все под foo:

foo/type_A_1
foo/type_A_2
foo/type_B_1
foo/type_B_2
foo/type_B_xx
foo/something_else

Я тоже попробовал print -l foo/*~type_Bи получил то же самое.

Как работает подстановочный знак исключения ~в Zsh?

Амелио Васкес-Рейна
источник

Ответы:

10

Вы должны включить каталог в исключение: print -l foo/*~foo/type_A*или print -l foo/*~{foo/type_A*}.

Если вы хотите, вы можете заменить каталог подстановочным знаком: print -l foo/*~*/type_A*

jofel
источник
Благодарность! Что касается второго паттерна, не могли бы вы объяснить, как он foo/*~*/type_A*работает? Второй *расширяется до каждой папки в рабочем каталоге, или он достаточно умен, чтобы расширяться только до foo?
Амелио Васкес-Рейна
@roseck Поскольку он кажется очень быстрым (например, когда вы запускаете print *~**/*в /каталоге), я предполагаю, что он сначала раскрывает первый шаблон, а затем удаляет все совпадения, которые соответствуют шаблону исключения.
Джофель
2
@roseck ~является чисто текстовым, часть перед раскрытием, как обычно, будет ~расширяться, а затем часть после удаления совпадает. Ofjofel Лучшим тестом было бы print /**/*~*: вы можете наблюдать, как оно проходит по всему дереву, даже если оно ничего не печатает.
Жиль "ТАК - перестань быть злым"
Я думал, что он хотел исключить type_B, но включить type_A.
Системович
Правильный ответ ниже
Арындин
30

У zsh есть ^оператор glob, когда EXTENDED_GLOB включен. Похоже, идеально подходит для вашей заявленной ситуации:

setopt extendedglob
print -rl foo/^type_A*

Это означает «сопоставлять что-либо, кроме того, что соответствует следующему шаблону», но его эффект ограничен частью шаблона между косыми чертами, или между началом шаблона и первым слешем, или (как в этом случае) между последним косая черта и конец рисунка.

Вы можете просмотреть опции zsh , которые в данный момент включены:

setopt

И отключите EXTENDED_GLOB с помощью:

unsetopt extendedglob
Крис Джонсен
источник