¿Cómo extraer el nombre de archivo sin la extensión de una ruta completa?

10

Estoy tratando de corregir mi primer script bash, y en un momento se pasa un nombre de archivo al script como $1. Necesito extraer el nombre del archivo sin la extensión.
Actualmente, supongo que todas las extensiones son tres letras, así que elimino los últimos 4 caracteres para obtener el nombre del archivo:

a="${1:0:-4}"

Pero necesito poder trabajar con extensiones que tengan más de tres caracteres, como %~n1en Windows.
¿Hay alguna forma de extraer el nombre del archivo sin la extensión de los argumentos?

usuario304822
fuente
stackoverflow.com/questions/2664740/…
sancho.s ReinstateMonicaCellio

Respuestas:

27

La forma habitual de hacer esto en bash es usar la expansión de parámetros. (Consulte la página de manual de bash y busque "Expansión de parámetros").

a=${1%.*}

El %indica que todo lo que coincida con el patrón siguiente ( .*) desde la derecha, utilizando la coincidencia más corta posible, se eliminará del parámetro $1. En este caso, no necesita comillas dobles (") alrededor de la expresión.

garyjohn
fuente
1
Los patrones de archivo son generalmente así: "Something.eng.ext". Obviamente, en este caso, ext es la extensión, pero el uso de $ {1%. *} Devolverá solo la parte "Algo", ¿verdad?
user304822
2
No. ${1%.*}volveremos Something.eng. Si desea quitar todo a la derecha de la primera, .incluido ., use ${1%%.*}, que volverá Something.
garyjohn
13

Si conoce la extensión, puede usar basename

$ basename /home/jsmith/base.wiki .wiki
base
Steven Penny
fuente
0

One-liner en Bash sin usar basename :

$ s=/the/path/foo.txt
$ echo "$(b=${s##*/}; echo ${b%.*})"
foo
LuckyDams
fuente