Quiero escribir un script para devolver solo la extensión del nombre del archivo de entrada. Por ejemplo, textfile.txt debería devolver txt. 
Soy nuevo en Linux y bash, y «m tratando de aprender a escribir guiones básicos. ¡Gracias!
Comentarios
Responder
El shell, bash por ejemplo, tiene muchos características de manipulación de cadenas . Uno de ellos le permite eliminar todo hasta un patrón determinado:
${VAR##GLOB}  La sintaxis anterior elimina todo de la variable $VAR hasta la primera coincidencia del glob GLOB. Entonces, para imprimir la extensión de un archivo sin su nombre, puede hacer: 
$ file="file.txt" $ echo ${file##*.} txt Tenga en cuenta que esto también puede tratar con más de una «extensión»:
$ file="file.new.txt" $ echo ${file##*.} txt  Si no quiere eso, use una # en su lugar, que eliminará la coincidencia más corta de los más largos: 
$ echo ${file#*.} new.txt Ahora, para ejecutar esto en todos los archivos de un directorio, puede hacer:
$ ls file.avi file.pdf file.png file.txt $ for file in *; do echo "$file : ${file##*.}"; done file.avi : avi file.pdf : pdf file.png : png file.txt : txt  Y, en aras de la integridad, también puede obtener el nombre del archivo sin su extensión usando ${file%.*}: 
$ for file in *; do echo "$file : ${file##*.} : ${file%.*}"; done file.avi : avi : file file.pdf : pdf : file file.png : png : file file.txt : txt : file Comentarios
- esto no ‘ t funciona para cosas como foo / .git / bar / baz Supongo que podrías hacer echo test.txt | awk -F ‘ / ‘ ‘ {print $ NF} ‘ | awk -F ‘. ‘ ‘ {print $ NF} ‘
- @PaulM ¿qué quieres decir? Ese ‘ es un archivo sin extensión, ¿qué esperarías obtener de eso?
- echo » / foo /var/.git/foo/bar.bz» | awk -F ‘ / ‘ ‘ {print $ NF} ‘ | awk -F ‘. ‘ ‘ {print $ NF} ‘ == > > bz
-  @PaulM file="/foo/var/.git/foo/bar.bz"; echo "${file##*.}":bz. No ‘ no veo ningún problema.
Responder
Con expansión de parámetros :
$ x="textfile.txt" $ echo ${x##*.} txt  El ${parameter##word} elimina el prefijo más grande que coincide con word (todo excepto el final del archivo). 
Respuesta
Un script bash muy simple que podría hacer lo que usted quisiera sería el siguiente:
#!/usr/bin/env bash echo "$1" | awk -F "." "{print $NF}"  El script se invoca como script.sh test.txt, y lo que hace es 
- 
imprime $1en stdout.$1es el primer parámetro dado al script, en este casotest.txt.
- 
la salida estándar de echose canaliza a stdin paraawkque divide la cadena (test.txt) en.y luego imprime el último elemento de la división (txten este caso).
Solo un pequeño comentario, esto se puede hacer con una sola línea porque es una tarea bastante simple:
echo test.txt | awk -F "." "{print $NF}" Comentarios
-  Debe agregar comillas alrededor de $1, o corre el riesgo de romper los nombres de archivos que contienen espacios, etc.
- esto no ‘ t funciona para cosas como foo / .git / bar / baz Supongo que podrías hacer echo test.txt | awk -F ‘ / ‘ ‘ {print $ NF} ‘ | awk -F ‘.’ ‘ {print $ NF} ‘
Responder
#!/bin/bash my_file=`basename "$1"` # get full file name as a script parameter and strip the path my_extension="${my_file##*.}" my_file="${my_file%.*}" # will return base file name before the extension echo "$my_file" echo "$my_extension" Ejecutar:
./script.sh index.html Salida:
index html Más información: Expansión de parámetros de shell | gnu.org
Respuesta
Para hacerlo, hay varias advertencias a tener en cuenta:
-  El archivo foo.d/barno tiene extensión, no es un archivofoocon un.d/barextensión.
-  También puede considerar que .bashrcno tiene extensión
-  El .y..probablemente deberían tratarse de forma especial y se debería considerar que no tienen ninguna extensión.
-  ¿Para qué es la extensión? file.tar.gz?gzotar.gz? ¿Qué pasa conholiday.picture.jpgobash-4.4?
-  ¿Qué debe devolver para foo.d/? ¿Vacío od?
Aquí, «haría:
#! /bin/sh - for file do case ${file##*/} in (?*.*) ext=${file##*.};; (*) ext=;; esac printf "%s\n" "$ext" done Comentarios
- Excelente respuesta que maneja también las advertencias habituales y código útil especialmente como función.
Respuesta
 Incluiré algunas opciones más en caso de que tenga sed o Perl instalado: 
 #!/bin/bash ext=$(<<<"$1" sed -n "s/^[^.]*\.//p") printf "Extension: $ext\n" ext=$(<<<"$1" perl -ne "s/^.*?\.//&&print") printf "Extension: $ext\n" exit 0  
-  s/^[^.]*\.//pensedys/^.*?\.//&&printenperl: intente sustituir la secuencia más corta de caracteres que no sea.seguido de un carácter.al comienzo de la cadena; si se pudo realizar la sustitución, imprima el resultado de la sustitución;
 % bash script.sh file.bin Extension: bin Extension: bin  
Respuesta
 Tenga cuidado. En Unix / Linux (y MacOS), la «extensión del nombre de archivo» es solo informativa (si es que tanto). Puede tener perfectamente un script en Perl llamado photo.gif, o un archivo GIF llamado poem.txt. O incluso un archivo llamado some.txt.png. 
Comentarios
- Es ‘ es tan informativo en MS Windows, ‘ es solo que allí el programa de shell predeterminado hace suposiciones más sólidas sobre el emparejamiento de extensión – contenido, y debería haber un desajuste entre el nombre y el contenido, todo el asunto generalmente comienza a gritar errores, lo pobre.
linux-4.2.3.tar.xzque puede descargar desde kernel.org ? ¿Cuál es la extensión del archivo/bin/bashque sin duda está disponible en su sistema? Verá, el concepto de » extensión de archivo » es bastante extraño en Linux. La parte que sigue al punto tiene muy poca importancia para el sistema; es más bien una indicación para el usuario de lo que puede esperar de ese archivo. Y esa señal puede mentir o estar equivocada.