2010-10-26 174 views
19

LEER DETENIDAMENTE: Esto es un poco inusual y tendrá la tentación de decir cosas como "que no es cómo usar una expresión regular" o "amigo, simplemente use String.SubString() ", etc ...Regex para obtener texto ENTRE dos caracteres

tengo una necesidad de escribir una expresión regular (por usar un método de pre-existente) que coincide con el texto entre corchetes, pero no el rizado apoyos a sí mismos.

Por ejemplo: "{} MatchThisText" Y "La la la MatchThisText {} la la la ..."
caso de que ambos partidos: "MatchThisText"

Someone asked this exact question a year ago, y él Obtuve un montón de soluciones para las expresiones regulares que coincidirán con las llaves, además de "MatchThisText", lo que da como resultado una coincidencia de "{MatchThisText}", que no es lo que él (o yo) necesitamos.

Si alguien puede escribir un Regex que realmente coincida solo con los caracteres ENTRE las llaves, realmente lo agradecería. Debe permitir cualquier valor ASCII, y debe detener la coincidencia en el PRIMER intervalo de cierre.

Por ejemplo: "{retailCategoryUrl}/{filtros}"
debe coincidir: retailCategoryUrl y filtros
Pero no coinciden: "retailCategoryUrl}/{filtros" (Todo menos las llaves exteriores)

Oye, esto es realmente complicado para mí, así que por favor, perdonen la pregunta si esto es trivial para algunos de ustedes.

GRACIAS!

+0

Muy fácil (requiere agrupación, pero honestamente, esta es una característica bastante fundamental), a menos que desee tener en cuenta los apoyos anidados "correctamente" (por ejemplo, como analizadores completos), en cuyo caso es simplemente imposible (excepto cuando se usan extensiones no-regex-y que algunas implementaciones, por ejemplo, NET, tienen). – delnan

+0

Necesitaremos más contexto, ya que la solución probablemente involucraría a los operadores mirar hacia atrás y mirar hacia adelante, así que dependa del dialecto de la expresión regular que esté usando. –

+0

'{(\ w +)}' - los corchetes denotan un grupo, del cual puedes obtener el contenido. –

Respuesta

17

Python:

(?<={)[^}]*(?=}) 

En contexto:

#!/usr/bin/env python 

import re 

def f(regexStr,target): 
    mo = re.search(regexStr,target) 
    if not mo: 
     print "NO MATCH" 
    else: 
     print "MATCH:",mo.group() 

f(r"(?<={)[^}]*(?=})","{MatchThisText}") 
f(r"(?<={)[^}]*(?=})","La la la {MatchThisText} la la la...") 

impresiones:

MATCH: MatchThisText 
MATCH: MatchThisText 
+1

observe que a veces tendrá que escapar '{' usando algo como: '(? <= \ {) [^ \}] * (? = \})' Porque algunos las aplicaciones intentarán pensar en los corchetes como operadores de repetición. – andi

8

Usted necesitará un operador de juego no expansivo, *?, a parar el partido tan pronto como el motor vea una abrazadera de cierre. Luego, debe agrupar lo que está dentro de las llaves usando paréntesis. Esto debe hacerlo:

{(.*?)} 

A continuación, tendrá que obtener el valor de group número 1 en su API de expresiones regulares. (¿Cómo se hace eso depende de su lenguaje de programación/API.)

+0

Muy útil, gracias! – mdegges

12

Si está utilizando un motor de búsqueda hacia delante con RegExp y el apoyo de búsqueda hacia atrás como Python, entonces se puede utilizar

/(?<={)[^}]*(?=})/

Si no es así 't (como javascript), puede usar /{([^}]*)}/ y obtener la coincidencia de subcadena.Javascript ejemplo:

"{foo}".match(/{([^}]*)}/)[1] // => 'foo'

0

current answer obras con .NET expresión regular, pero que tenga que quitar las llaves de todos los partidos:

var regex = new Regex(@"(?<={)[^}]*(?=})", RegexOptions.Compiled); 
var results = regex.Matches(source) 
        .Cast<Match>() 
        .Select(m => m.Value.TrimStart('{').TrimEnd('}')); 
0

en JavaScript se obtiene una matriz con todos los partidos. Aquí hay un ejemplo que machtes texto entre css` y `para machting cadenas de la plantilla:

yourstring.match(/css`([^}]+).`/gmi) 
Cuestiones relacionadas