Você não recebe um aviso em bash
, você recebe um erro por ls
(você verá que ls
status de saída é não -0, que indica que falhou).
Em zsh
e bash
, {...}
não é um operador de globbing, é uma expansão que ocorre antes da globulação.
Em:
ls -d -- *.{dot,svg,err}
(você esqueceu o -d
e o --
btw), o shell expande o {...}
primeiro:
ls -d -- *.dot *.svg *.err
e depois faz o glob. bash
, como a maioria das shells parecidas com Bourne, tem essa característica errada de que globs não correspondentes são passados como estão. Enquanto em zsh
, um glob não correspondente é um erro.
Veja como rm -f [ab].c
in bash
poderia excluir o arquivo [ab].c
se não houvesse nenhum arquivo chamado a.c
nor b.c
. Em zsh
, você receberia um erro no match . Veja a opção failglob
em bash
para obter um comportamento semelhante.
ls -d -- *.{dot,svg,err}(N)
em zsh
habilitaria a opção nullglob
em todos os 3 globs, de modo que, se os globs não corresponderem, eles serão removidos, mas provavelmente não é o que você deseja, porque nenhum dos globs corresponde a nenhum arquivo , o comando se tornará:
ls -d --
Que listará .
(o diretório atual).
Melhor é usar um glob que corresponda aos arquivos com uma das três extensões:
ls -d -- *.(dot|svg|err)
Isso fornecerá uma lista classificada de arquivos para ls
, ls
será executada, a menos que não haja nenhum arquivo que corresponda a esse padrão.
Você também tem a opção de ativar o comportamento sh
/ bash
(bogus IMO) com emulate sh
ou com unsetopt nomatch
. Uma abordagem um pouco melhor é ativar o comportamento csh
(que também era o comportamento de shells Unix antes da liberação do shell Bourne):
setopt cshnullglob
Com essa opção, o comando é cancelado apenas se all as globs na linha de comando não corresponderem. Se pelo menos uma corresponder, todas as que não corresponderem serão removidas, então:
ls -d -- *.{dot,svg,err}
Expandirá os dot
, svg
e err
, omitindo os que faltam.
Se você quiser comparar o efeito na ordem dos argumentos das diferentes abordagens, você precisa de um comando que (ao contrário de ls
) não os ordene antes de exibir. Com GNU ls
, você pode passar a opção -U
para isso, ou desde que ls
imprima seus argumentos aqui, use apenas printf '%s\n' *...
.