2009-07-23 17 views
13

He estado buscando a través de SO y aunque esta pregunta ha sido contestada en un escenario:expresión regular para que coincida con un patrón, pero excluye un conjunto de palabras

Regex to match all words except a given list

No es exactamente lo que estoy buscando . Estoy tratando de escribir una expresión regular que coincida con cualquier cadena de la forma [\ w] + [(], pero que no coincide con las tres cadenas "cat (", "dog (" y "sheep ("). Específicamente.

he estado jugando con la búsqueda hacia delante y de búsqueda hacia atrás, pero no acabo de llegar allí. me puede complicar esto, por lo que cualquier ayuda sería muy apreciada.

Respuesta

21

Si la aplicación de expresiones regulares apoya look-ahead or look-behind assertions, se puede usar lo siguiente:

  • Usando una afirmación negativa de preanálisis:

    \b(?!(?:cat|dog|sheep)\()\w+\(
    
  • El uso de un negativo de observación detrás de la afirmación:

    \b\w+\((?<!\b(?:cat|dog|sheep)\() 
    

que añade el \b ancla que marca un word boundary. Por lo tanto, catdog( se emparejaría aunque contenga dog(.

Pero mientras las aserciones de previsión son más ampliamente compatibles con las implementaciones de expresiones regulares, la expresión regular con la aserción es más eficiente ya que solo se prueba si la expresión regular anterior (en nuestro caso \b\w+\() ya coincidía. Sin embargo, la afirmación de anticipación se probaría antes de con la que correspondería la real. Por lo tanto, en nuestro caso, la afirmación de anticipación se prueba siempre que coincida \b.

+1

es más probable eficiente ya que no comprueba cada posición individual con una visión hacia adelante negativo El segundo (vale la pena señalar que son negativos.) Además, estoy pensando que podría ser mejor poner el negativo mirar hacia atrás después del paréntesis e incluir un paréntesis en el look-behind. De esta forma, solo realizará una búsqueda adicional detrás una vez que encuentre una posible coincidencia, en lugar de cada palabra en la cadena. – Blixt

+0

@Blixt: Buen punto. – Gumbo

+0

Además, su primera expresión regular rechazará 'catástrofe (' 'dogmática (' y 'sheepily ('. Su segunda se salvó de un error similar por el '\ b' en el aspecto subyacente. – rampion

3

¿Realmente requieren esto en una sola expresión regular? Si no es así, la implementación más simple es solo dos expresiones regulares, una para comprobar que no coincide con una de sus palabras prohibidas, y otra para que coincida con su \ w +, encadenada con un Y lógico.

Cuestiones relacionadas