Estoy tratando de dividir una cadena en dos partes usando regex. La cadena tiene el siguiente formato:
text to extract<number>
He estado usando (.*?)<y <(.*?)>que funcionan bien, pero después de leer un poco en regex, comencé a preguntarme por qué necesito ?las expresiones. Solo lo hice así después de encontrarlos a través de este sitio, así que no estoy exactamente seguro de cuál es la diferencia.

Respuestas:
Es la diferencia entre cuantificadores codiciosos y no codiciosos.
Considere la entrada
101000000000100.Utilizando
1.*1,*es codicioso - que coincidirá con todo el camino hasta el final, y luego dar marcha atrás hasta que pueda coincidir1, dejándole con1010000000001..*?No es codicioso.*no coincidirá con nada, pero luego intentará hacer coincidir caracteres adicionales hasta que coincida1, finalmente coincidirá101.Todos los cuantificadores tienen un modo no expansivo:
.*?,.+?,.{2,6}?, e incluso.??.En su caso, un patrón similar podría ser
<([^>]*)>: emparejar cualquier cosa menos un signo mayor que (estrictamente hablando, coincide con cero o más caracteres que no sean>intermedios<y>).Ver la hoja de trucos del cuantificador .
fuente
?difiere del no codicioso???"abc", la expresión regular/\w\w?\w/coincidiría con la cadena completa"abc", porque?es codiciosa./\w\w??\w/es vago, solo coincidirá"ab". Solo retrocederá y coincidirá"abc"si falla más tarde.En codicioso vs no codicioso
La repetición en regex por defecto es codiciosa : intentan igualar tantas repeticiones como sea posible, y cuando esto no funciona y tienen que retroceder, intentan igualar una repetición menos a la vez, hasta que coincida con todo el patrón. encontró. Como resultado, cuando finalmente ocurre una coincidencia, una repetición codiciosa coincidiría con tantas repeticiones como sea posible.
El
?cuantificador como repetición cambia este comportamiento a no codicioso , también llamado reacio ( en, por ejemplo, Java ) (y a veces "perezoso"). En contraste, esta repetición primero intentará igualar la menor cantidad posible de repeticiones, y cuando esto no funciona y tienen que retroceder, comienzan a emparejar un reptil más a la vez. Como resultado, cuando finalmente ocurre una coincidencia, una repetición reacia coincidiría con la menor cantidad posible de repeticiones.Referencias
Ejemplo 1: de la A a la Z
Comparemos estos dos patrones:
A.*ZyA.*?Z.Dada la siguiente entrada:
Los patrones producen las siguientes coincidencias:
A.*Zproduce 1 partido:AiiZuuuuAoooZ( ver en rubular.com )A.*?Zproduce 2 coincidencias:AiiZyAoooZ( ver en rubular.com )Primero centrémonos en lo que
A.*Zhace. Cuando coincide con el primeroA, el.*, siendo codicioso, primero intenta igualar tantos.como sea posible.Como
Zno coincide, el motor retrocede, y.*luego debe coincidir con uno menos.:Esto sucede algunas veces más, hasta que finalmente llegamos a esto:
Ahora
Zpuede coincidir, por lo que el patrón general coincide:Por el contrario, la repetición reacia en los
A.*?Zprimeros partidos lo menos.posible, y luego tomar más.según sea necesario. Esto explica por qué encuentra dos coincidencias en la entrada.Aquí hay una representación visual de lo que coincidieron los dos patrones:
Ejemplo: una alternativa
En muchas aplicaciones, las dos coincidencias en la entrada anterior es lo que se desea, por lo tanto,
.*?se utiliza un reacio en lugar del codicioso.*para evitar la coincidencia excesiva. Sin embargo, para este patrón en particular, existe una alternativa mejor, utilizando la clase de caracteres negados.El patrón
A[^Z]*Ztambién encuentra las mismas dos coincidencias que elA.*?Zpatrón para la entrada anterior ( como se ve en ideone.com ).[^Z]es lo que se llama una clase de caracteres negados : coincide con cualquier cosa menosZ.La principal diferencia entre los dos patrones está en el rendimiento: al ser más estricta, la clase de caracteres negados solo puede coincidir en un sentido para una entrada determinada. No importa si usa un modificador codicioso o reacio para este patrón. De hecho, en algunos sabores, puedes hacerlo aún mejor y usar lo que se llama cuantificador posesivo, que no retrocede en absoluto.
Referencias
Ejemplo 2: de A a ZZ
Este ejemplo debería ser ilustrativo: muestra cómo los patrones de clase de caracteres codiciosos, renuentes y negados coinciden de manera diferente dada la misma entrada.
Estas son las coincidencias para la entrada anterior:
A[^Z]*ZZproduce 1 coincidencia:AuuZZ( como se ve en ideone.com )A.*?ZZproduce 1 coincidencia:AiiZooAuuZZ( como se ve en ideone.com )A.*ZZproduce 1 coincidencia:AiiZooAuuZZeeeZZ( como se ve en ideone.com )Aquí hay una representación visual de lo que coincidieron:
Temas relacionados
Estos son enlaces a preguntas y respuestas en stackoverflow que cubren algunos temas que pueden ser de interés.
Una repetición codiciosa puede superar a otra
fuente
Digamos que tienes:
<(.*)>coincidiríaa></adonde<(.*?)>coincidiríaa. Este último se detiene después del primer partido de>. Comprueba una o 0 coincidencias de.*seguido por la siguiente expresión.La primera expresión
<(.*)>no se detiene cuando coincide con la primera>. Continuará hasta el último partido de>.fuente