2008-09-29 11 views
110

Necesito sustituir el valor de una cadena en mi expresión regular en Ruby. ¿Hay una forma fácil de hacer esto? Por ejemplo:Interpolando una cadena en una expresión regular

foo = "0.0.0.0" 
goo = "here is some other stuff 0.0.0.0" 
if goo =~ /value of foo here dynamically/ 
    puts "success!" 
end 
+0

¿Estás tratando de ver si foo es una subcadena de goo? No creo que esté claro lo que estás preguntando. – Neall

+0

Si es así, ¡goo.include? (Foo) es suficiente. –

+1

No, no estaba tratando de ver si foo es una subcadena de goo; También necesitaba capturar algo, por lo tanto, incluir no funcionó. –

Respuesta

209

Igual que la inserción de cadenas.

if goo =~ /#{Regexp.quote(foo)}/ 
#... 
+9

El código Wow Ruby tiene una belleza intrínseca. – Fuser97381

3

Uso Regexp.new:

if goo =~ Regexp.new(foo) # Evaluates to /0.0.0.0/ 
6

Probablemente Regexp.escape(foo) sería un punto de partida, pero hay una buena razón por la que no se puede utilizar la expresión interpolación más convencional: "my stuff #{mysubstitutionvariable}"?

Además, puede usar !goo.match(foo).nil? con una cadena literal.

6
Regexp.compile(Regexp.escape(foo)) 
-2
foo = "0.0.0.0" 
goo = "here is some other stuff 0.0.0.0" 

puts "success!" if goo =~ /#{foo}/ 
+2

No, esto dará un "error" erróneo para "aquí hay otras cosas 070x0! 0", porque los puntos son comodines de expresiones regulares. –

+0

good catch glenn. –

89

Tenga en cuenta que la Regexp.quote en Jon L.'s answer es importante!

if goo =~ /#{Regexp.quote(foo)}/ 

Si usted acaba de hacer lo "obvio" versión:

if goo =~ /#{foo}/ 

entonces los períodos en su texto partido son tratados como comodines de expresiones regulares, y "0.0.0.0" coincidirá "0a0b0c0".

Tenga en cuenta también que si lo que realmente quieres para comprobar si hay una coincidencia de subcadena, sólo tiene que hacer

if goo.include?(foo) 

que no requiere cita o preocuparse por caracteres especiales adicionales.

+0

¡Ah, gran captura, Glenn! ¡Gracias! –

+2

Tenga en cuenta que lo contrario (no usar '.quote()') también puede ser útil si está buscando construir una expresión regular usando una cadena. – Jesse

+0

"si realmente quiere comprobar si hay una coincidencia de subcadena, simplemente puede hacer' si goo.include?(foo) '" => Verdadero cuando estás interesado en verificar la existencia. Si estás interesado en reemplazar y ya estás usando String.gsub, entonces Regexp.quote puede ser tu única opción. –

2

Aquí hay una limitada pero útil otra respuesta:

descubrí que lo que puedo insertar fácilmente en una expresión regular sin utilizar Regexp.quote o Regexp.escape si acabo de utilizar comillas simples en mi cadena de entrada: (una IP dirección coincidente)

IP_REGEX = '\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}' 

my_str = "192.0.89.234 blahblah text 1.2, 1.4" # get the first ssh key 
# replace the ip, for demonstration 
my_str.gsub!(/#{IP_REGEX}/,"192.0.2.0") 
puts my_str # "192.0.2.0 blahblah text 1.2, 1.4" 

comillas simples solo interpretar \\ y \ '.

http://en.wikibooks.org/wiki/Ruby_Programming/Strings#Single_quotes

Esto me ayudó cuando necesitaba usar la misma porción larga de una expresión regular varias veces. No es universal, pero cabe el ejemplo de la pregunta, creo.

+0

tengo curiosidad por lo que se pensará de mi publicación aquí, pero yo duda de que se verá tan abajo ahora. – Plasmarob

+0

comentarios son mucho más útiles que un voto a la baja. – Plasmarob

Cuestiones relacionadas