¿Cuál es la diferencia entre a[bc]dy a{b,c}d? ¿Por qué la gente usa a{b,c}dcuando ya existe a[bc]d?
brace-expansion
pattern-matching
Weijun Zhou
fuente
fuente

command a[bc]d?lsy solo prueba caracteres únicos, parecería que funcionan igual.Respuestas:
Los dos son bastante diferentes.
a[bc]des un patrón de nombre de archivo (en shells que no seanfish). Se expandirá a los dos nombres de archivoabdy,acdsi son nombres de archivos existentes en el directorio actual.La
[...]parte es una expresión entre corchetes que coincide con un solo carácter de los enumerados (o elementos de clasificación cuando se incluyen rangos). Para que coincida con el patróna[bc]d, el carácter entre las cadenasayden un nombre de archivo debe ser abo ac.Si
abdexiste, peroacdno existe, entonces solo se expandiríaabdy viceversa.Si ninguno
abd, niacdexistir, dependiendo de la cáscara y las opciones, que daría lugar a un error (Unix originalsh,(t)csh,zsh,fish,bash -O failglob) y posiblemente salir de la cáscara, o salir de la unexpanded¹ patrón (Bourne-como yrc-como conchas) o ampliar a nada (bash/zsh/yash -o nullglobalgunas versiones anteriores defishUnix originalshy(t)cshsi hay otros globos coincidentes en el mismo comando).a{b,c}des una expansión de llaves (en conchas que las admiten). Se expandirá a las dos cadenasabdyacd.La
{...}parte es un conjunto delimitado por comas de cadenas (en este ejemplo, en algunos cáscara, también puede ser un intervalo tal comoa..ko20..25o más avanzadas que son como00..20..2o0..20..2%02d), y la expansión se calcula mediante la combinación de cada una de estas cadenas con el flanqueo cuerdasayd. Estas cadenas podrían ser más largas que un solo personaje y también podrían ser expansiones de llaves.La expansión ocurre independientemente de si estas cadenas corresponden a nombres de archivos existentes o no.
Si está construyendo cadenas, use una expansión de llaves. Si está haciendo coincidir nombres de archivo, use un patrón de nombre de archivo.
¹ En este caso particular,
a[bc]dpodría ser el nombre de un archivo existente, por lo que es potencialmente peligroso usar cosas comorm -f ./*.[ch]en esos shells yrm -f ./*.{c,h}es un problema menor.fuente
a{b,c}d, las partesbycno necesitan ser letras individuales; por ejex{ten,ci}sion. Mientrasex[tenci]siono lo que sea solo coincidirá con una de estas letras.a[bc]des coincidencia de patrones y es parte del estándar POSIX. En POSIX, esto se introduce como la "expresión de paréntesis de patrón". Está documentado en la sección 2.13 del manual.La Sección 2.13.3 también menciona algo que se comporta de manera diferente de lo que uno esperaría para las expresiones regulares habituales cuando se usa para la expansión de nombre de archivo (énfasis por mí)
a{b,c}des una expansión de llaves , no está en la especificación de POSIX. Aquí está la parte correspondiente del manual de bash (énfasis por mí):Según el comentario de @mosvy, esto apareció por primera vez,
cshpero el comportamientobashes diferentecshy de otros shells. Este tipo de expansión de llaves también está presente englob(3).Hay otro tipo de expansión de llaves
{a..z}que solo apareció después debash3.0, y hay más agregadas enbash4.0.En un shell donde está activado el globbing, ejecutar en una carpeta vacía, se devuelve el siguiente resultado
En respuesta al comentario de @ Jesse_b, si estás en un shell interactivo y ambos aplican,
a[bc]des menos difícil escribir. Por ejemplogrep pattern [ab][12].txt.fuente
csh, mucho antesbash. También está presente en la función de biblioteca glob (3). La diferencia es quebashse realiza antes de otras expansiones:a=A; ab=A/B; ac=A/C; echo $a{b,c}funcionará en bash de manera diferente a cualquier otro shell.