Espressione regolare per rimuovere l’estensione di un file

Ho bisogno di un’espressione regolare che possa rimuovere l’estensione di un nome file, restituendo solo il nome del file.

Ecco alcuni esempi di input e output:

myfile.png -> myfile myfile.png.jpg -> myfile.png 

Ovviamente posso farlo manualmente (cioè rimuovendo tutto dall’ultimo punto) ma sono sicuro che esiste un’espressione regolare che può farlo da sola.

Solo per la cronaca, lo sto facendo in JavaScript

 /(.*)\.[^.]+$/ 

Il risultato sarà in quel primo gruppo di acquisizione. Tuttavia, è probabilmente più efficiente trovare la posizione del periodo più a destra e quindi prendere tutto prima di esso, senza usare espressioni regolari.

Solo per completezza: come si può ottenere senza le espressioni regolari?

 var input = 'myfile.png'; var output = input.substr(0, input.lastIndexOf('.')) || input; 

|| input || input prende cura del caso, dove lastIndexOf() fornisce un -1 . Vedi, è ancora un solitario.

 /^(.+)(\.[^ .]+)?$/ 

Casi di test in cui questo funziona e altri falliscono:

  • “.htaccess” (periodo iniziale)
  • “file” (nessuna estensione file)
  • “invia a mrs.” (nessuna estensione, ma finisce in abbr.)
  • “versione 1.2 del progetto” (nessuna estensione, ma contiene ancora un punto)

Il thread comune sopra è, naturalmente, estensioni di file “malformate”. Ma devi sempre pensare a quei casi d’angolo. : P

Casi di test in cui ciò non riesce:

  • “versione 1.2” (nessuna estensione di file, ma “appare” per averne una)
  • “name.tar.gz” (se la vedi come “estensione composta” e vuoi dividerla in “nome” e “.tar.gz”)

Come gestirli è problematico e meglio deciso in base a un progetto specifico.

 /^(.+)(\.[^ .]+)?$/ 

Il modello sopra è sbagliato – includerà sempre anche l’estensione. È a causa di come funziona il motore regex javascript. Il token (\.[^ .]+) È facoltativo, quindi il motore corrisponderà correttamente all’intera stringa con (.+) http://cl.ly/image/3G1I3h3M2Q0M


Ecco la mia soluzione regexp testata.

Il modello corrisponderà a filenameNoExt con / senza estensione nel percorso, rispettando i separatori barra e barra rovesciata

 var path = "c:\some.path/subfolder/file.ext" var m = path.match(/([^:\\/]*?)(?:\.([^ :\\/.]*))?$/) var fileName = (m === null)? "" : m[0] var fileExt = (m === null)? "" : m[1] 

dissezione del modello sopra:

 ([^:\\/]*?) // match any character, except slashes and colon, 0-or-more times, // make the token non-greedy so that the regex engine // will try to match the next token (the file extension) // capture the file name token to subpattern \1 (?:\. // match the '.' but don't capture it ([^ :\\/.]*) // match file extension // ensure that the last element of the path is matched by prohibiting slashes // capture the file extension token to subpattern \2 )?$ // the whole file extension is optional 

http://cl.ly/image/3t3N413g3K09

http://www.gethifi.com/tools/regex

Questo coprirà tutti i casi menzionati da @RogerPate ma includendo anche percorsi completi

L’espressione regolare per abbinare il modello è:

 /\.[^.]*$/ 

Trova un carattere punto ( \. ), Seguito da 0 o più caratteri che non sono punti ( [^.] * ), Seguito dalla fine della stringa ( $ ).

un altro no regex modo di farlo la versione “oposite” o di Raul (non usando pop () per rimuovere)

Non è necessario fare riferimento alla variabile due volte, quindi è più semplice da allineare

 filename.split('.').slice(0,-1).join() 

Questo lo farà pure 🙂

 'myfile.png.jpg'.split('.').reverse().slice(1).reverse().join('.'); 

Mi assocerei comunque all’espressione regolare … = P

  return filename.split('.').pop(); 

farà avverare il tuo desiderio. Ma non il modo di espressione regolare.

In javascript puoi chiamare il metodo Replace () che sostituirà in base a un’espressione regolare.

Questa espressione regolare combacia con tutto dall’inizio della linea fino alla fine e rimuove qualsiasi cosa dopo l’ultimo periodo incluso il periodo.

 /^(.*)\..*$/ 

Il modo di implementare la sostituzione può essere trovato in questa domanda StackOverflow.

Domanda regex di Javascript