2011-12-07 7 views
12

Si hago esto:¿Por qué no es un error de sintaxis?

(false true) 

falla con un error de sintaxis, como espero. Pero si hago esto:

(false 
true) 

se ejecuta el código, y se tira a la basura la primera condición y devuelve el resultado de la segunda.

¿Esto se considera un error o de una pieza?

+8

'(falso; cierto)' –

+2

sabía que tenía que haber una explicación sencilla. Debe publicar esto como una respuesta real y reclamar algo de crédito para usted. :-) – L2G

Respuesta

15

Los finales de línea son opcionales, por lo que en este caso, el retorno está causando el analizador interpretarlo como la siguiente:

(false; true) 

que será evaluado simplemente:

(true) 

Si estos fueran método llamadas entonces ambos serían evaluados, pero solo los últimos serían emitidos. Por ejemplo:

x = (p "hello" 
p "world" 
2) 

Esta voluntad de salida "hola" y "mundo" y x será igual a 2

7

paréntesis se usan para agrupar, saltos de línea se utilizan como separadores de expresión. Entonces, lo que tienes aquí es simplemente un grupo de dos expresiones. No hay nada que rechazar

Esto es útil porque de este idioma conocido:

def foo(bar = (bar_set = true; :baz)) 
    if bar_set 
    # optional argument was supplied 
    end 
end 

Simplemente no hay otra manera en Ruby para averiguar si un argumento opcional se suministra o no.

Básicamente, esto se convierte en interesante en presencia de efectos secundarios, tales como la asignación de una variable en mi ejemplo o la impresión de la pantalla en el ejemplo de @ 32bitkid. En su ejemplo, no hay ningún efecto secundario, es por eso que no podía ver lo que estaba en realidad pasando.

+0

En realidad, ese modismo es nuevo para mí, ¡así que agradezco su respuesta! – L2G

+0

@ L2G: no se utiliza muy a menudo, pero hay algunos protocolos estándar que requieren que distinguen entre si o no se suministra un argumento opcional. 'inject' es un ejemplo. Por lo general, se implementa en C o Java o C#, con acceso privilegiado a las partes internas del intérprete, lo que facilita la verificación de la existencia de un argumento opcional. Pero si quiere duplicar su comportamiento en Ruby puro, debe recurrir a trucos como este. –

2

Rubí le puede dar una advertencia si tiene advertencias sobre.

$VERBOSE = true 
def foo 
    (false 
    true) 
end 

le da

(irb):3: warning: unused literal ignored 

Tanto en Rubí 1.9.1 Patchlevel 378 y Ruby 1.8.7 Patchlevel 330.

Ver How can I run all Ruby scripts with warnings? de cómo ejecutar todos los scripts de Ruby con advertencias sobre.

Cuestiones relacionadas