Me atendré a las funciones de secuencias de comandos. Las características interactivas ricas (edición de línea de comandos, finalización, indicaciones, etc.) tienden a ser muy diferentes, logrando efectos similares de maneras totalmente incompatibles. ¿Qué características están en zsh y faltan en bash, o viceversa? da algunos consejos sobre el uso interactivo.
Lo más parecido a bash sería ATT ksh93 o mksh (el shell Korn y un clon). Zsh también tiene un subconjunto de características, pero necesitaría ejecutarlo en modo de emulación ksh, no en modo nativo de zsh.
No enumeraré las características de POSIX (que están disponibles en cualquier sh
shell moderno ), ni las características relativamente oscuras, ni las características mencionadas anteriormente para uso interactivo. Las observaciones son válidas a partir de bash 4.2, ksh 93u y mksh 40.9.20120630 como se encuentra en Debian wheezy.
$'…'
(cadenas literales con interpolación de barra invertida) está disponible en ksh93 y mksh. `$" ... "(cadenas traducidas) es específico de bash.
Mksh y ksh93 tienen que fallar ;&
en una case
declaración, pero no ;;&
para probar casos posteriores. Mksh tiene ;|
para eso, y mksh reciente permite ;;&
compatibilidad.
((…))
Las expresiones y [[ … ]]
pruebas aritméticas son características de ksh. Algunos operadores condicionales son diferentes, consulte "expresiones condicionales" a continuación.
Ksh y bash tienen coprocesos pero funcionan de manera diferente.
Mksh y ksh93 admiten la function name {…}
sintaxis de las definiciones de funciones además del estándar name () {…}
, pero el uso function
de ksh cambia las reglas de alcance, por lo que name () …
debe mantener la compatibilidad. Las reglas para los caracteres permitidos en los nombres de funciones varían; atenerse a los caracteres alfanuméricos y _
.
Ksh93 y mksh admiten la expansión de llaves {foo,bar}
. Ksh93 admite rangos numéricos {1..42}
pero mksh no.
Ksh93 y apoyo extracción mksh subcadena con ${VAR:offset}
y ${VAR:offset:length}
, pero no como el caso plegable ${VAR^}
, ${VAR,}
, etc Usted puede hacer la conversión caso typeset -l
y typeset -u
tanto en bash y ksh.
Admiten el reemplazo con ${VAR/PATTERN/STRING}
o ${VAR/PATTERN//STRING}
. Las reglas de comillas para STRING son ligeramente diferentes, por lo tanto, evite las barras invertidas (y tal vez otros caracteres) en STRING (cree una variable y ${VAR/PATTERN/$REPLACEMENT}
úsela si el reemplazo contiene caracteres de comillas).
Expansión Array ( ${ARRAY[KEY]}
, "${ARRAY[@]}"
, ${#ARRAY[@]}
, ${!ARRAY[@]}
) de trabajo en bash como en ksh.
${!VAR}
expandiéndose a ${OTHERVAR}
cuando el valor de VAR
is OTHERVAR
(referencia de variable indirecta) es específico de bash (ksh hace algo diferente con ${!VAR}
). Para obtener esta doble expansión en ksh, debe usar una referencia de nombre en su lugar ( typeset -n VAR=OTHERVAR; echo "$VAR"
). ${!PREFIX*}
funciona igual
Proceso de sustitución <(…)
y >(…)
se admite en ksh93 pero no en mksh.
Los patrones de globo extendido ksh que deben shopt -s extglob
activarse en bash siempre están disponibles en ksh93 y mksh.
Mksh no admite clases de personajes como [[:alpha:]]
.
Bash y ksh93 definen pseudo-archivos y , pero mksh no./dev/tcp/HOST/PORT
/dev/udp/HOST/PORT
La expansión de comodines en una redirección en los scripts (como por var="*.txt"; echo hello >$a
escrito a.txt
si ese nombre de archivo es la única coincidencia para el patrón) es una característica específica de bash (otros shells nunca lo hacen en scripts).
<<<
Las cadenas aquí funcionan en ksh como en bash.
El acceso directo >&
para redirigir errores de sintaxis también es compatible con mksh pero no con ksh93.
[[ … ]]
sintaxis de doble soporte
La sintaxis de doble parche de ksh es compatible con ATT ksh93 y mksh como en bash.
Operadores de archivos
Ksh93, mksh y bash admiten las mismas extensiones de POSIX, incluso -a
como sinónimo obsoleto de -e
, -k
(adhesivo), -G
(propiedad de egid), -O
(propietario de euid), -ef
(mismo archivo), -nt
(más nuevo que), -ot
(más antiguo que).
-N FILE
(modificado desde la última lectura) no es compatible con mksh.
Mksh no tiene un operador de coincidencia de expresiones regulares =~
. Ksh93 tiene este operador, y realiza la misma coincidencia que en bash, pero no tiene el equivalente de BASH_REMATCH
recuperar grupos coincidentes después.
Operadores de cadenas
Ksh93 y mksh admiten los mismos operadores de comparación de cadenas <
y >
bash, así como el ==
sinónimo de =
. Mksh no utiliza la configuración regional para determinar el orden lexicográfico, compara cadenas como cadenas de bytes.
Otros operadores
-v VAR
para probar si una variable está definida es específica de bash. En cualquier shell POSIX, puede usar [ -z "${VAR+1}" ]
.
El conjunto de caracteres permitidos en los nombres de alias no es el mismo en todos los shells. Creo que es lo mismo que para las funciones (ver arriba).
Ksh93 tiene una llamada incorporada builtin
, pero no ejecuta un nombre como un comando incorporado. Se usa command
para omitir alias y funciones; Esto llamará a un incorporado si existe, de lo contrario, un comando externo (puede evitar esto con PATH= command error_out_if_this_is_not_a_builtin
).
Esto es específico de bash. Usted puede obtener un efecto similar con .sh.fun
, .sh.file
y .sh.lineno
en ksh93. En mksh hay al fin LINENO
.
declare
es un nombre específico de bash para ksh's typeset
. Uso typeset
: también funciona en bash.
Mksh define local
como un alias para typeset
. En ksh93, debe usar typeset
(o definir un alias).
Mksh no tiene matrices asociativas (están programadas para una versión aún no publicada).
No creo que haya un equivalente exacto de bash typeset -t
(función de rastreo) en ksh.
Ksh93 no tiene -e
.
Ksh93 y mksh procesan las opciones -e
y -n
como en bash. Mksh también entiende -E
, ksh93 no lo trata como una opción. La expansión de barra invertida está desactivada de forma predeterminada en ksh93, activada de forma predeterminada en mksh.
Ksh no proporciona una forma de deshabilitar los comandos incorporados. Para evitar una construcción, busque la ruta del comando externo e invoque explícitamente.
Ksh93 tiene -a
pero no -l
. Mksh no tiene ninguno.
Ni ksh93 ni mksh lo han hecho export -n
. Use en su typeset +x foo
lugar, funciona en bash y ksh.
Ksh no exporta funciones a través del entorno.
let
es lo mismo en bash y ksh.
Esta es una característica específica de bash. Puede usar while read
bucles o sustitución de comandos para leer un archivo y dividirlo en una matriz de líneas. Cuida IFS
y pega. Aquí está el equivalente de mapfile -t lines </path/to/file
:
IFS=$'\n'; set -f
lines=($(</path/to/file))
unset IFS; set +f
printf
Es muy similar. Creo que ksh93 es compatible con todas las directivas de formato de bash. mksh no es compatible con %q
o %(DATE_FORMAT)T
; en algunas instalaciones, printf
no es un mksh incorporado y llama al comando externo en su lugar.
printf -v VAR
es específico de bash, ksh siempre imprime en salida estándar.
Varias opciones son específicas de bash, incluidas todas las de readline. Las opciones -r
, -d
, -n
, -N
, -t
, -u
son idénticos en bash, ksh93 y mksh.
Puede declarar una variable como de solo lectura en Ksh93 y mksh con la misma sintaxis. Si la variable es una matriz, primero debe asignarla y luego hacerla de solo lectura con readonly VAR
. Las funciones no se pueden hacer de solo lectura en ksh.
Todas las opciones set
y set -o
son características de POSIX o ksh.
shopt
es específico de bash. Muchas opciones se refieren al uso interactivo de todos modos. Para conocer los efectos sobre el globbing y otras funciones habilitadas por algunas opciones, consulte la sección "Opciones" a continuación.
Esta variante de .
existe en ksh también. En bash y mksh, source
busca el directorio actual después PATH
, pero en ksh93, es un equivalente exacto de .
.
La DEBUG
pseudo-señal no se implementa en mksh. En ksh93, existe con una forma diferente de informar información, consulte el manual para más detalles.
En ksh, type
es un alias para whence -v
. En mksh, type -p
no imprime la ruta al ejecutable, sino un mensaje legible por humanos; necesitas usar whence -p COMMAND
en su lugar.
Opciones
shopt -s dotglob
- no ignore los archivos de puntos en globbing
Para emular la dotglob
opción en ksh93, puede configurar FIGNORE='@(.|..)'
. No creo que haya algo así en mksh.
shopt -s extglob
- patrones de globo extendido ksh
La extglob
opción siempre está activada en ksh.
shopt -s failglob
- error si un patrón global no coincide con nada
No creo que esto exista ni en mksh ni en ksh93. Lo hace en zsh (comportamiento por defecto a menos que null_glob
o csh_null_glob
son set).
Ksh93 tiene globbing recursivo con **/
, habilitado con set -G
. Mksh no tiene globulación recursiva.
shopt -s lastpipe
- ejecuta el último comando de una tubería en el shell principal
Ksh93 siempre ejecuta el último comando de una tubería en el shell principal, que en bash requiere lastpipe
que se establezca la opción. Mksh siempre ejecuta el último comando de una tubería en una subshell.
shopt -s nocaseglob
, shopt -s nocasematch
- patrones que no distinguen entre mayúsculas y minúsculas
Mksh no tiene coincidencia de patrones sin distinción entre mayúsculas y minúsculas. Ksh93 lo admite patrón por patrón: prefije el patrón con ~(i)
.
shopt -s nullglob
- expande patrones que no coinciden con ningún archivo a una lista vacía
Mksh no tiene esto. Ksh93 lo admite patrón por patrón: prefije el patrón con ~(N)
.
Obviamente, la mayoría de las BASH_xxx
variables no existen en ksh. $BASHPID
se puede emular con el costoso pero portátil sh -c 'echo $PPID'
, y se ha agregado recientemente a mksh. BASH_LINE
está .sh.lineno
en ksh93 y LINENO
en mksh. BASH_SUBSHELL
está .sh.subshell
en ksh93.
Mksh y ksh93 obtienen el archivo proporcionado ENV
cuando se inician.
EUID
y UID
no existen en ksh93. Mksh los llama USER_ID
y KSH_UID
; que no tiene GROUPS
.
FUNCNAME
y FUNCNEST
no existen en ksh. Ksh93 tiene .sh.fun
y .sh.level
. Las funciones declaradas con function foo { …; }
(¡sin paréntesis!) Tienen su propio nombre $0
.
GLOBIGNORE
existe en ksh93 pero con un nombre y una sintaxis diferentes: se llama FIGNORE
y es un patrón único, no una lista separada por dos puntos. Usa un @(…|…)
patrón. Ksh FIGNORE
subsume bash, con una sintaxis completamente diferente.
Ksh93 y mksh no tienen nada como HOSTTYPE
, MACHTYPE
y OSTYPE
. Ni SHELLOPTS
o TIMEFORMAT
.
Mksh sí PIPESTATUS
, pero ksh93 no.
Mksh y ksh93 tienen RANDOM
.