Vou me ater aos recursos de script. Recursos interativos avançados (edição de linha de comando, conclusão, prompts etc.) tendem a ser muito diferentes, atingindo efeitos semelhantes de maneiras totalmente incompatíveis. Quais recursos estão no zsh e estão ausentes no bash ou vice-versa? fornece algumas dicas sobre o uso interativo.
A coisa mais próxima do bash seria ATT ksh93 ou mksh (o shell Korn e um clone). O Zsh também possui um subconjunto de recursos, mas você precisará executá-lo no modo de emulação ksh, não no modo nativo do zsh.
Não listarei os recursos do POSIX (disponíveis em qualquer shshell moderno ), nem os recursos relativamente obscuros, nem os mencionados acima, para uso interativo. As observações são válidas a partir do bash 4.2, ksh 93u e mksh 40.9.20120630, conforme encontrado no Debian wheezy.
$'…'(cadeias literais com interpolação de barra invertida) está disponível em ksh93 e mksh. `$" ... "(cadeias traduzidas) é específico do bash.
Mksh e ksh93 precisam ;&passar por uma casedeclaração, mas não ;;¶ testar casos subseqüentes. Mksh tem ;|isso, e mksh recente permite ;;&compatibilidade.
((…))expressões e [[ … ]]testes aritméticos são recursos do ksh. Alguns operadores condicionais são diferentes, consulte "expressões condicionais" abaixo.
Ksh e bash têm coprocessos, mas funcionam de maneira diferente.
Mksh e ksh93 suportam a function name {…}sintaxe das definições de funções além do padrão name () {…}, mas usando as functionregras de escopo das mudanças no ksh, portanto, mantenha a name () …compatibilidade. As regras para caracteres permitidos nos nomes das funções variam; atenha-se a alfanuméricos e _.
Ksh93 e mksh suportam expansão de chaves {foo,bar}. O Ksh93 suporta intervalos numéricos, {1..42}mas o mksh não.
Ksh93 e extração mksh apoio substring com ${VAR:offset}e ${VAR:offset:length}, mas não caso dobrar como ${VAR^}, ${VAR,}, etc. Você pode fazer a conversão caso typeset -le typeset -uem ambos bash e ksh.
Eles suportam a substituição com ${VAR/PATTERN/STRING}ou ${VAR/PATTERN//STRING}. As regras de citação para STRING são um pouco diferentes, portanto, evite barras invertidas (e talvez outros caracteres) em STRING (crie uma variável e use-a ${VAR/PATTERN/$REPLACEMENT}se a substituição contiver caracteres de citação).
Expansão Array ( ${ARRAY[KEY]}, "${ARRAY[@]}", ${#ARRAY[@]}, ${!ARRAY[@]}) o trabalho em bash como em ksh.
${!VAR}expandindo para ${OTHERVAR}quando o valor de VARé OTHERVAR(referência variável indireta) é específico do bash (o ksh faz algo diferente com ${!VAR}). Para obter essa dupla expansão no ksh, você precisa usar uma referência de nome ( typeset -n VAR=OTHERVAR; echo "$VAR"). ${!PREFIX*}funciona da mesma maneira.
Substituição de processo <(…)e >(…)é suportado no ksh93, mas não no mksh.
Os padrões glob estendidos do ksh que precisam shopt -s extglobser ativados no bash estão sempre disponíveis no ksh93 e no mksh.
Mksh não suporta classes de personagens como [[:alpha:]].
Bash e ksh93 definem pseudo-arquivos e , mas mksh não./dev/tcp/HOST/PORT/dev/udp/HOST/PORT
A expansão de curingas em um redirecionamento em scripts (como por var="*.txt"; echo hello >$aescrito, para a.txtse esse nome de arquivo for a única correspondência para o padrão) é um recurso específico do bash (outros shells nunca fazem isso em scripts).
<<< as strings here funcionam no ksh como no bash.
O atalho >¶ redirecionar erros de sintaxe também é suportado pelo mksh, mas não pelo ksh93.
[[ … ]] sintaxe de colchete duplo
A sintaxe de colchete duplo do ksh é suportada pelo ATT ksh93 e pelo mksh como no bash.
Operadores de arquivo
Ksh93, mksh e suporte do bash as mesmas extensões para POSIX, incluindo -acomo um sinônimo obsoleta de -e, -k(pegajosa), -G(propriedade da egid), -O(proprietário por euid), -ef(mesmo arquivo), -nt(mais recente do que), -ot(acima de).
-N FILE (modificado desde a última leitura) não é suportado pelo mksh.
Mksh não tem um operador de correspondência de regexp =~. O Ksh93 possui esse operador e executa a mesma correspondência que no bash, mas não tem o equivalente BASH_REMATCHa recuperar grupos correspondidos posteriormente.
Operadores de string
Ksh93 e mksh suportam os mesmos operadores de comparação de cadeias <e >bash, além do ==sinônimo =. Mksh não usa configurações de localidade para determinar a ordem lexicográfica, ele compara cadeias como cadeias de bytes.
Outros operadores
-v VARpara testar se uma variável está definida é específico do bash. Em qualquer shell POSIX, você pode usar [ -z "${VAR+1}" ].
O conjunto de caracteres permitidos nos nomes alternativos não é o mesmo em todos os shells. Eu acho que é o mesmo que para funções (veja acima).
O Ksh93 possui um builtinbuilt-in chamado , mas não executa um nome como um comando interno . Use commandpara ignorar aliases e funções; isso chamará um builtin, se houver, caso contrário, um comando externo (você pode evitar isso com PATH= command error_out_if_this_is_not_a_builtin).
Isso é específico do bash. Você pode obter um efeito semelhante com .sh.fun, .sh.filee .sh.linenono ksh93. Em mksh, finalmente LINENO.
declareé um nome específico do bash para ksh's typeset. Uso typeset: ele também funciona no bash.
Mksh define localcomo um alias para typeset. No ksh93, você precisa usar typeset(ou definir um alias).
Mksh não possui matrizes associativas (elas estão previstas para uma versão ainda não lançada).
Eu não acho que exista um equivalente exato do bash typeset -t(função trace) no ksh.
Ksh93 não tem -e.
Ksh93 e mksh processam as opções -ee -ncomo no bash. Mksh também entende -E, o ksh93 não o trata como uma opção. A expansão da barra invertida está desativada por padrão em ksh93, ativada por padrão em mksh.
O Ksh não fornece uma maneira de desativar os comandos internos. Para evitar um builtin, procure o caminho do comando externo e chame-o explicitamente.
Ksh93 tem -amas não -l. Mksh não tem nenhum.
Nem ksh93 nem mksh tem export -n. Em typeset +x foovez disso, use em bash e ksh.
O Ksh não exporta funções através do ambiente.
let é o mesmo no bash e no ksh.
Este é um recurso específico do bash. Você pode usar while readloops ou substituição de comando para ler um arquivo e dividi-lo em uma matriz de linhas. Cuide IFSe globbing. Aqui está o equivalente a mapfile -t lines </path/to/file:
IFS=$'\n'; set -f
lines=($(</path/to/file))
unset IFS; set +f
printfé muito parecido. Eu acho que o ksh93 suporta todas as diretivas de formato do bash. mksh não suporta %qou %(DATE_FORMAT)T; em algumas instalações, printfnão é um mksh embutido e chama o comando externo.
printf -v VAR é específico do bash, o ksh sempre imprime na saída padrão.
Várias opções são específicas do bash, incluindo todas sobre o readline. As opções -r, -d, -n, -N, -t, -usão idênticos em bash, ksh93 e mksh.
Você pode declarar uma variável como somente leitura no Ksh93 e mksh com a mesma sintaxe. Se a variável for uma matriz, você precisará atribuir a ela primeiro e depois torná-la somente leitura com readonly VAR. As funções não podem ser feitas somente leitura em ksh.
Todas as opções para sete set -osão recursos POSIX ou ksh.
shopté específico do bash. Muitas opções dizem respeito ao uso interativo de qualquer maneira. Para efeitos sobre globos e outros recursos ativados por algumas opções, consulte a seção “Opções” abaixo.
Esta variante de .existe também no ksh. No bash e mksh, sourcepesquisa o diretório atual depois PATH, mas no ksh93, é um equivalente exato de ..
O DEBUGpseudo-sinal não é implementado no mksh. No ksh93, ele existe com uma maneira diferente de relatar informações, consulte o manual para obter detalhes.
No ksh, typeé um apelido para whence -v. No mksh, type -pnão imprime o caminho para o executável, mas uma mensagem legível por humanos; você precisa usar whence -p COMMANDem seu lugar.
Opções
shopt -s dotglob - não ignore arquivos de ponto no globbing
Para emular a dotglobopção no ksh93, você pode definir FIGNORE='@(.|..)'. Eu não acho que exista algo assim no mksh.
shopt -s extglob - padrões estendidos ksh de glob
A extglobopção está efetivamente sempre ativada em ksh.
shopt -s failglob - erro se um padrão glob não corresponder a nada
Eu não acho que isso exista no mksh ou no ksh93. Ele faz em zsh (comportamento padrão, a menos null_globou csh_null_globsão set).
O Ksh93 possui globbing recursivo com **/, ativado com set -G. Mksh não tem globbing recursivo.
shopt -s lastpipe - execute o último comando de um pipeline no shell pai
O Ksh93 sempre executa o último comando de um pipeline no shell pai, que no bash requer que a lastpipeopção seja definida. Mksh sempre executa o último comando de um pipeline em um subshell.
shopt -s nocaseglob, shopt -s nocasematch- padrões que não diferenciam maiúsculas de minúsculas
Mksh não possui correspondência de padrão que não diferencia maiúsculas de minúsculas. O Ksh93 o suporta padrão por padrão: prefixe o padrão com ~(i).
shopt -s nullglob - expanda padrões que não correspondem a nenhum arquivo para uma lista vazia
Mksh não tem isso. O Ksh93 o suporta padrão por padrão: prefixe o padrão com ~(N).
Obviamente, a maioria das BASH_xxxvariáveis não existe no ksh. $BASHPIDpode ser emulado com o caro, mas portátil sh -c 'echo $PPID'e foi adicionado recentemente ao mksh. BASH_LINEestá .sh.linenoem ksh93 e LINENOem mksh. BASH_SUBSHELLestá .sh.subshellem ksh93.
Mksh e ksh93 fornecem o arquivo fornecido ENVquando são inicializados.
EUIDe UIDnão existe no ksh93. Mksh os chama USER_IDe KSH_UID; não tem GROUPS.
FUNCNAMEe FUNCNESTnão existe em ksh. Ksh93 tem .sh.fune .sh.level. As funções declaradas com function foo { …; }(sem parênteses!) Têm seu próprio nome $0.
GLOBIGNOREexiste no ksh93, mas com um nome e sintaxe diferentes: é chamado FIGNOREe é um padrão único, não uma lista separada por dois-pontos. Use um @(…|…)padrão. O Ksh substitui o FIGNOREbash's, com uma sintaxe totalmente diferente.
Ksh93 e mksh não têm nada como HOSTTYPE, MACHTYPEe OSTYPE. Nem SHELLOPTSou TIMEFORMAT.
Mksh tem PIPESTATUS, mas ksh93 não.
Mksh e ksh93 têm RANDOM.