Aquí está la solución simple que probablemente debería usar:
mv filename.gif filename.gif.keep
rm *.gif
mv filename.gif.keep filename.gif
La .keepextensión no tiene nada de especial , esto solo hace que el nombre de archivo no termine temporalmente .gif.
Si no debe cambiar el nombre del archivo (y hay situaciones de secuencias de comandos donde esto es importante):
for X in *.gif; do
if [ "$X" != "filename.gif" ]; then
rm "$X"
fi
done
O puedes escribirlo más corto así:
for X in *.gif; do [ "$X" != "filename.gif" ] && rm "$X"; done
Puede preferir usar finden su lugar; es muy poderoso, podría considerarlo más legible, y maneja mejor los nombres de archivos extraños con caracteres como *en ellos .
find . -maxdepth 1 -not -name 'filename.gif' -name '*.gif' -delete
He utilizado el -notoperador para facilitar la lectura, pero si el cumplimiento de POSIX es importante, si no está utilizando GNU find, o si se trata de un script que tiene la intención de redistribuir a otros o ejecutar en una variedad de sistemas, debería use el !operador en su lugar:
find . -maxdepth 1 ! -name 'filename.gif' -name '*.gif' -delete
Una cosa útil findes que puede modificar fácilmente el comando para que no se distinga entre mayúsculas y minúsculas, para que también encuentre y elimine archivos con extensiones como .GIF:
find . -maxdepth 1 -not -name 'filename.gif' -iname '*.gif' -delete
Tenga en cuenta que he utilizado -inameen lugar de -namepara el patrón de búsqueda *.gif, pero he no utilizado para filename.gif. Presumiblemente, usted sabe exactamente cómo se llama su archivo y -inamecoincidirá con mayúsculas alternativas no solo en la extensión , sino en cualquier parte del nombre del archivo.
Todas estas soluciones solo eliminan archivos que residen inmediatamente en el directorio actual . No eliminan archivos no contenidos en el directorio actual, y no eliminan archivos que residen en subdirectorios del directorio actual.
Si desea eliminar archivos en todas partes contenidos en el directorio actual (es decir, incluidos en subdirectorios, y en subdirectorios de esos subdirectorios, etc. - archivos contenidos en el directorio actual o cualquiera de sus descendientes), use find sin maxdepth -1 :
find . -not -name 'filename.gif' -name '*.gif' -delete
¡Ten cuidado con esto!
También puede establecer otros valores con -maxdepth. Por ejemplo, para eliminar archivos en el directorio actual y sus hijos y nietos pero no más profundo:
find . -maxdepth 3 -not -name 'filename.gif' -name '*.gif' -delete
¡Solo asegúrate de nunca poner -deleteprimero, antes de las otras expresiones! Verás que siempre pongo -deleteal final. Si lo pones al principio, se evaluaría primero, y todos los archivos debajo .(incluidos los archivos que no terminan en .gify los archivos en los directorios sub-sub-sub-sub profundos ... .) se eliminarán.
Para obtener más información , ver las páginas del manual para bashy shy para los comandos utilizados en estos ejemplos: mv, rm, [, y (especialmente) find.
find, que es muy versátil.findes de hecho un buen hallazgo.findmaneja los nombres de archivos extraños con*ellos mejor que el for-loop? El bucle for maneja los archivos con*multa, porque ha usado comillas dobles.Si está utilizando
bash(el shell predeterminado), laextglobopción de shell le permite usar una sintaxis extendida de coincidencia de patrones. Para habilitarlo, use elshoptcomando incorporado:(Incluyo esa línea en mi
.bashrcarchivo).Entre otras cosas, otorga acceso al
!()operador, que coincide con cualquier patrón que no se encuentre dentro de los elementos parentales. Para su propósito:Hay más información disponible en
man bash"Coincidencia de patrones".fuente
extglobdebe habilitarse, pero no pasa nada malo si está deshabilitada (en ese caso, esto simplemente no funciona). Y parece estar habilitado de manera predeterminada, aunque no tengoshopt -s extglobninguno de mis archivos de configuración (o los globales). Si hay una explicación simple de por qué me funciona de manera inmediata, puede agregarla a esta respuesta; o puedo publicar una nueva pregunta.Abra una Terminal con Ctrl+ Alt+ Ty escriba:
La diferencia entre
-deletey-exec rm -vf {} \;es que con la segunda opción, podrá ver qué archivos se han eliminado, debido a la-vbandera. Eso es algo que no se puede hacer con la-deleteopción. (-name -deleteImprimirá los nombres de archivo, perormcon-vrevela si cada archivo fue exitosamente eliminado.)fuente
Ahí está la
GLOBIGNOREvariable. Deman bash:Entonces, una forma simple es establecer
GLOBGINOREel nombre de archivo en cuestión:Entonces, en tu caso:
Por supuesto, dado que
GLOBIGNOREcontiene patrones, puede usarlo siempre que desee excluir un patrón:Una ventaja (?!)
GLOBIGNOREEs que su configuración excluye automáticamente.y..de ser emparejado, y permitedotglob:Entonces, una forma simple de eliminar todos los archivos y carpetas en un directorio:
El
*coincidirá con nombres de archivo que comienzan con., yaGLOBIGNOREhabilitadadotglob, pero no va a coincidir.o.., por lo que no afectará el directorio padre de esa manera.fuente