2010-02-20 12 views

risposta

394

Greedy consumerà il più possibile. Da http://www.regular-expressions.info/repeat.html vediamo l'esempio di cercare di abbinare i tag HTML con <.+>. Supponiamo di avere il seguente:

<em>Hello World</em> 

Si può pensare che <.+> (. mezzi ogni carattere che non a capo e + significa uno o più) corrisponderebbe solo alle <em> e la </em>, quando in realtà lo farà sii molto avido e vai dal primo < all'ultimo >. Ciò significa che corrisponderà a <em>Hello World</em> anziché a quello che volevi.

Rendendolo pigro (<.+?>) impedirà questo. Aggiungendo ? dopo il +, diciamo di ripetere il più volte possibile, quindi il primo > che incontra è dove vogliamo interrompere la corrispondenza.

Ti incoraggio a scaricare RegExr, un ottimo strumento che ti aiuterà a esplorare le espressioni regolari - lo uso sempre.

+1

quindi se usi avido avrai 3 corrispondenze (1 elemento + 2 tag) o solo 1 partita (1 elemento)? – ajsie

+8

Corrisponde solo 1 volta, a partire dal primo ** <** e termina con l'ultimo **> **. – Sampson

+2

Ma renderlo pigro corrisponderebbe due volte, dandoci sia il tag di apertura che di chiusura, ignorando il testo nel mezzo (poiché non si adatta all'espressione). – Sampson

41

Greedy significa che l'espressione corrisponde a un gruppo il più ampio possibile, pigro significa che corrisponderà al gruppo più piccolo possibile. Per questa stringa:

abcdefghijklmc 

e questa espressione:

a.*c 

Una partita avido corrisponderà l'intera stringa, e un match pigro corrisponderà solo il primo abc.

+0

+1 http://www.regular-expressions.info/repeat.html – Sampson

182

"Greedy" significa abbinare la stringa più lunga possibile.

'Lazy' significa abbinare la stringa più breve possibile.

Per esempio, gli avidi h.+l partite 'hell' nel 'hello' ma il pigro h.+?l partite 'hel'.

+44

Brillante , così pigro si fermerà non appena la condizione l è soddisfatta, ma avido significa che si fermerà solo una volta che la condizione l non sarà più soddisfatta? –

+0

Per tutte le persone che leggono il post: quantificatori avidi o pigri da soli non corrisponderanno alla sottostringa più lunga/più breve possibile. Dovresti usare un [** token goloso temperato **] (http://www.rexegg.com/regex-quantifiers.html#tempered_greed), o usare approcci non-regex. –

+0

@AndrewS Non essere confuso dal doppio ll nell'esempio. È piuttosto pigro che si abbinerà alla sottostringa più breve possibile, mentre avido si abbinerà al più lungo possibile. Greedy 'h. + L' corrisponde a '' helol'' in '' helolo'' ma il pigro' h. +? L' corrisponde a '' hel''. –

4

Da Regular expression

I quantificatori standard nei regolari espressioni sono avidi, nel senso che incontro quanto più possibile, solo dando indietro come necessario per corrispondere alla resto della regex.

Utilizzando un quantificatore pigro, l'espressione tenta innanzitutto la corrispondenza minima .

7

Tratto da www.regular-expressions.info

Golosità: quantificatori Greedy prima cerca di ripetere il token il numero di volte possibile, e gradualmente cede partite come il motore marcia indietro per trovare delle partite in generale.

Pigrizia: Pigro quantifier primo ripete il token come poche volte, come richiesto, e espande gradualmente la partita come il motore marcia indietro attraverso l'espressione regolare per trovare una corrispondenza complessiva.

40
+-------------------+-----------------+------------------------------+ 
| Greedy quantifier | Lazy quantifier |  Description   | 
+-------------------+-----------------+------------------------------+ 
| *     | *?    | Star Quantifier: 0 or more | 
| +     | +?    | Plus Quantifier: 1 or more | 
| ?     | ??    | Optional Quantifier: 0 or 1 | 
| {n}    | {n}?   | Quantifier: exactly n  | 
| {n,}    | {n,}?   | Quantifier: n or more  | 
| {n,m}    | {n,m}?   | Quantifier: between n and m | 
+-------------------+-----------------+------------------------------+ 

Aggiungi un? a un quantificatore per renderlo ungreedy i.e pigro.

Esempio:
stringa prova: StackOverflow
espressione reg avida: s.*o uscita: stackoverflo w
reg espressione lazy: s.*?o uscita: stacko verflow

+1

non è ?? equivalente a ? . Allo stesso modo, non è {n}? equivalente a {n} –

+1

@BreakingBenjamin: no ?? non è equivalente a?, quando ha la possibilità di restituire 0 o 1 occorrenza, sceglierà l'alternativa 0 (pigro). Per vedere la differenza, confronta 're.match ('(f)? (. *)', 'Food'). Groups()' a 're.match ('(f) ?? (. *)', ' cibo '). I gruppi() '. In quest'ultimo, '(f) ??' non combacerà con la 'f' iniziale, anche se potrebbe. Quindi la 'f' verrà abbinata dal secondo gruppo di cattura '. *'. Sono sicuro che puoi costruire un esempio con '{n}?' pure. Certamente questi due sono usati raramente. – smci

-2

cercare di capire il seguente comportamento:

var input = "0014.2"; 

Regex r1 = new Regex("\\d+.{0,1}\\d+"); 
Regex r2 = new Regex("\\d*.{0,1}\\d*"); 

Console.WriteLine(r1.Match(input).Value); // "0014.2" 
Console.WriteLine(r2.Match(input).Value); // "0014.2" 

input = " 0014.2"; 

Console.WriteLine(r1.Match(input).Value); // "0014.2" 
Console.WriteLine(r2.Match(input).Value); // " 0014" 

input = " 0014.2"; 

Console.WriteLine(r1.Match(input).Value); // "0014.2" 
Console.WriteLine(r2.Match(input).Value); // "" 
6

Per quanto ne so, la maggior parte del motore regex è avido di default. Aggiungi un punto interrogativo alla fine del quantificatore abiliterà la corrispondenza pigra.

Come @Andre S menzionato nel commento.

  • Greedy: continuare a cercare finché la condizione non è soddisfatta.
  • Lazy: interrompe la ricerca una volta soddisfatte le condizioni.

Fare riferimento all'esempio di seguito per ciò che è avido e cosa è pigro.

import java.util.regex.Matcher; 
import java.util.regex.Pattern; 

public class Test { 
    public static void main(String args[]){ 
     String money = "100000000999"; 
     String greedyRegex = "100(0*)"; 
     Pattern pattern = Pattern.compile(greedyRegex); 
     Matcher matcher = pattern.matcher(money); 
     while(matcher.find()){ 
      System.out.println("I'm greeedy and I want " + matcher.group() + " dollars. This is the most I can get."); 
     } 

     String lazyRegex = "100(0*?)"; 
     pattern = Pattern.compile(lazyRegex); 
     matcher = pattern.matcher(money); 
     while(matcher.find()){ 
      System.out.println("I'm too lazy to get so much money, only " + matcher.group() + " dollars is enough for me"); 
     } 
    } 
} 


Il risultato è:

Sono greeedy e voglio 100.000.000 di dollari. Questo è il massimo che posso ottenere.

sono troppo pigro per avere così tanti soldi, solo 100 dollari è abbastanza per me

+1

Mi piace molto il tuo esempio. – Xatenev

0

corrispondenza Greedy. Il comportamento predefinito delle espressioni regolari è essere avidi. Ciò significa che cerca di estrarre il più possibile finché non si conforma a un modello anche quando una parte più piccola sarebbe stata sintatticamente sufficiente.

Esempio:

import re 
text = "<body>Regex Greedy Matching Example </body>" 
re.findall('<.*>', text) 
#> ['<body>Regex Greedy Matching Example </body>'] 

anziché corrispondenti fino alla prima occorrenza di ‘>’, si estrae l'intera stringa. Questo è il comportamento avido predefinito o 'prendi tutto' di regex.

Lazy matching, d'altra parte, "prende il meno possibile". Questo può essere effettuato aggiungendo ? alla fine del pattern.

Esempio:

re.findall('<.*?>', text) 
#> ['<body>', '</body>'] 

Se si desidera solo la prima partita da recuperare, utilizzare il metodo di ricerca, invece.

re.search('<.*?>', text).group() 
#> '<body>' 

Fonte: Python Regex Examples

0

Greedy significa che sarà il vostro modello di consumare fino a quando non ce ne sono di loro a sinistra e si può guardare oltre.

Pigro si fermerà non appena incontrerà il primo modello richiesto.

Un esempio comune che incontro spesso è \s*-\s*? di una regex ([0-9]{2}\s*-\s*?[0-9]{7})

Il primo \s* è classificato come avidi a causa di * e cercherà di tanti spazi bianchi possibile dopo si incontrano le cifre e poi cercare un trattino carattere "-". Dove il secondo \s*? è pigro a causa del presente di *? che significa che apparirà il primo carattere di spazio bianco e si fermerà proprio lì.

Problemi correlati