Me he encontrado con patrones globales y comodines, y es de particular interés para mí [!]
.
Esta construcción es similar a la
[!]
construcción, excepto que, en lugar de hacer coincidir cualquier carácter dentro de los corchetes, coincidirá con cualquier carácter, siempre que no aparezca entre el[
y]
.
rm myfile [!192]
Lo anterior, creo, eliminará cualquier / todos los archivos, excepto cualquiera / todos los archivos que tengan 192 en su nombre.
Sin embargo, me preocupa el uso adecuado de esto con una extensión de archivo y, en particular, múltiples condiciones.
¿Cuál sería la sintaxis adecuada en tal situación?
rm myfile [!.gif .csv. mp3]
o
rm myfile [!.gif !.csv !.mp3]
Mi preocupación es que el período podría estar fuera de lugar, por lo que cualquier archivo con un .
(¿cuál sería alguno de ellos seguramente?) Luego sería manipulado, cuando estoy tratando de causar la manipulación de archivos específicos.
Esta construcción es similar a la [ ]
construcción, excepto que, en lugar de hacer coincidir cualquier carácter dentro de los corchetes, coincidirá con cualquier carácter, siempre que no aparezca entre el [
y ]
.
(Citado de http://www.tldp.org/LDP/GNU-Linux-Tools-Summary/html/x11655.htm )
Ahora; para mí, eso sugiere que un singular !
es suficiente, y todos los valores allí incluidos están contenidos dentro del rango.
fuente
ls my-pattern
oecho my-command
para verificar si el bloqueo se realiza de la manera que desea, antes de correrrm
[!]
es similar pero no como[!]
^
tiene exactamente el mismo significado que!
en este contexto, por lo tanto,[^a]
excluyea
exactamente como lo[!a]
hace: si el primer carácter que sigue a [es a! o un ^ entonces cualquier carácter no encerrado coincide. (man bash
)rm myfile [!192]
eliminarámyfile
, así como cualquier archivo de un solo carácter que no se llame1
,9
o2
.Respuestas:
Citando
man 7 glob
:El énfasis en la parte de un solo carácter aquí,
[]
no se puede usar para cadenas enteras en Bash Pattern Matching.bash
La expansión Brace se puede usar para unir cadenas, sin embargo, no hay forma (que yo sepa) de negarlas. P.ejse expande a
no importa si existen estos archivos.
Como señaló wchargin ,
shopt
se puede utilizar para habilitar operadores de coincidencia de patrones extendidos, uno de ellos es!()
. Después de corrershopt -s extglob
, p. Ej.se expande a
si esos archivos existen en el directorio actual. Para más información
man bash
(sección EXPANSIÓN / Expansión de nombre de ruta) y Expansión de nombre de ruta (globalización) .Para lo que estás tratando de hacer, siempre usaría
find
, que ofrece la negación y mucho más, por ejemplo, de la siguiente manera:Esto solo enumera los resultados, si desea eliminarlos simplemente agregue la
-delete
opción al final del comando. Como siempre con las acciones de eliminación: siempre verifique cuidadosamente primero .find
ofrece un montón de opciones útiles muy bien explicadas porman find
.fuente
find
comando es recursivo ( edición: como se mostró originalmente , podría guardar este comentario para la información adicional relevante pero no esencial que transmite). Para buscar archivos que residen solo en el directorio actual pero no también en sus subdirectorios, y, por lo tanto, solo elimine esos archivos si-delete
se agrega la acción, puede agregarlos-maxdepth 1
inmediatamente despuésfind .
. Esto lo alinearía con el efecto de globbing, ya que los globs no son recursivos en Bash a menos que laglobstar
opción de shell esté activada y**
se use. El globo que se muestra en la pregunta no es recursivo en todos los depósitos.shopt -s extglob
, se puede utilizarecho 1.!(gif|csv|mp3)
, que imprime todo1.ext
, dondeext
no esgif
,csv
omp3
. (Consulte la subsección "Coincidencia de patrones" deman bash
.)Creo que entendiste mal el uso de corchetes.
[abc]
coincide con uno de los caracteresa
,b
oc
.[!abc]
coincide con un carácter que no esa
,b
oc
. Entonces el comandoeliminará
myfile
y los archivos1
,9
y2
porque tiene un espacio entre myfile y el soporte. Por el contrario, el comandoeliminará los archivos
myfile1
,myfile9
ymyfile2
.fuente
find
.Los corchetes
[
]
denotan una clase de personaje. Cualquier personaje individual dentro de ellos puede coincidir en la posición dada. Entoncescoincide con tres nombres posibles:
No , no coincide
file192
, ya que sólo se ocupa del carácter individual despuésfile
.También podemos usar rangos entre paréntesis.
[0-9]
coincide con cualquier dígito en la posición dada. Para dos dígitos, necesitamos[0-9][0-9]
. Para un dígito seguido de una letra mayúscula, podríamos usar[0-9][A-Z]
...!
indica negacióncoincidirá con archivos que tengan un solo carácter después de
file
excepto1
o9
o2
. Por ejemplo, se emparejaráfile7
yfiles
efile%
(y muchos otros), pero nofile192
, ya que tiene dos caracteres adicionales.Para su caso de uso, sugiero usar en
find
lugar de[!]
. Cuenta con unnot
operador.También es recursivo , lo que significa que entra en todos los subdirectorios de forma predeterminada. Puede limitarlo al directorio actual con
-maxdepth 1
, si eso es lo que desea. Los comodines de shell (globbing) no son recursivos (aunque**
se puede habilitar el globbing recursivo con ).Suponiendo que no desea evitar eliminar enlaces simbólicos, podemos agregar
-type d
a las pruebas negadas para evitar eliminar cualquier directorio. Gracias a Eliah Kagan por esa sugerencia.Si ve lo que quiere, puede ejecutar el comando nuevamente con
-delete
fuente
[0-9a-fA-F]