Espressione regolare da fermare al primo incontro


532

Il mio schema regex sembra qualcosa del genere

<xxxx location="file path/level1/level2" xxxx some="xxx">

Sono interessato solo alla parte tra virgolette assegnate alla posizione. Non dovrebbe essere facile come sotto senza l'interruttore goloso?

/.*location="(.*)".*/

Non sembra funzionare.


Qual è la tua fonte, è HTML o XML o qualcosa del genere?
Oskar Kjellin,

20
Perché questa è una wiki della comunità? È una vera domanda. Troppo tardi adesso.
Ahmad Mageed,

1
In che lingua stai scrivendo? Si prega di non utilizzare regex per XML. Ci sono molti modi migliori per analizzare XML
Oskar Kjellin

3
Non se tutto ciò che vuoi è cercare attributi semplici. Regex è appropriato e più veloce.
codenheim,

Direi che se ad esempio il codice c # è molto meglio usare linq per questo. Dubito che sarà meglio regex se hai un buon parser
Oskar Kjellin

Risposte:


1097

Devi rendere la tua espressione regolare non avida, perché per impostazione predefinita, "(.*)"corrisponderà a tutti"file path/level1/level2" xxx some="xxx" .

Invece puoi rendere la tua dot-star non avida, il che lo farà corrispondere al minor numero possibile di caratteri:

/location="(.*?)"/

L'aggiunta di a ?su un quantificatore ( ?, *o +) lo rende non avido.


32
FWIW, in caso la vostra utilizzando VIM, questa regex bisogno di essere un po 'diverso: invece di .*?è .\{-}per una partita non avidi.
SooDesuNe,

44
Grazie Daniel. "L'aggiunta di un? Su un quantificatore (?, * O +) lo rende non avido." è un consiglio utile per me.
PhatHV,

10
Il ? descrive la mia confusione nel cercare di capirlo. Quanto appropriato.
Robbie Smith,

1
Credo che si possa dire "pigro" invece di "non avido"
Manticore,

50

location="(.*)"corrisponderà dal "dopo location=al" dopo a some="xxxmeno che tu non lo renda avido. Quindi è necessario .*?(cioè renderlo non avido) o meglio sostituirlo .*con [^"]*.


3
[^ "] * è probabilmente anche più veloce con la maggior parte dei motori regex perché non ha bisogno di cercare il modello dopo il modello corrente.
Jean Vincent

1
@Kip: Probabilmente hai ragione, ma la .*?notazione è più generale di[^"]*
Bondax

che ne dite se voglio includere il carattere delimitatore usando [^ "] *
Frohlich,

per niente, se non sai cosa significano ^ e [] qui. Molte persone capiranno. *
Vincent Gerris il

31

Che ne dite di

.*location="([^"]*)".*

Ciò evita la ricerca illimitata con. * E corrisponderà esattamente alla prima citazione.


A causa di discrepanze nel grep, quanto sopra dovrebbe essere il modello preferito se la portabilità è un problema.
Josh Habdas,

22

Usa una corrispondenza non avida, se il tuo motore lo supporta. Aggiungi il ? all'interno della cattura.

/location="(.*?)"/

11

L'uso di quantificatori pigri ?senza bandiera globale è la risposta.

Per esempio,

inserisci qui la descrizione dell'immagine

Se avessi avuto la bandiera globale /g, avrebbe abbinato tutte le partite di lunghezza più bassa come di seguito. inserisci qui la descrizione dell'immagine


1

Dato che stai usando un sottosuolo quantificato e come descritto in Perl Doc ,

Per impostazione predefinita, un modello secondario quantificato è " avido ", ovvero corrisponderà il maggior numero di volte possibile (data una particolare posizione iniziale) pur consentendo al resto del modello di corrispondere. Se si desidera che corrisponda al numero minimo di volte possibile, seguire il quantificatore con un "?" . Nota che i significati non cambiano, solo la "golosità":

*?        //Match 0 or more times, not greedily (minimum matches)
+?        //Match 1 or more times, not greedily

Pertanto, per consentire al modello quantificato di ottenere una corrispondenza minima, seguilo per ?:

/location="(.*?)"/

1

Ecco un altro modo.

Ecco quello che vuoi. Questo è pigro[\s\S]*?

Il primo articolo: [\s\S]*?(?:location="[^"]*")[\s\S]* Sostituisci con:$1

Spiegazione : https://regex101.com/r/ZcqcUm/2


Per completezza, questo ottiene l'ultimo. Questo è avido[\s\S]*

L'ultimo articolo:[\s\S]*(?:location="([^"]*)")[\s\S]* Sostituisci con:$1

Spiegazione : https://regex101.com/r/LXSPDp/3


C'è solo 1 differenza tra queste due espressioni regolari e questa è la ?

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.