¿Cuáles son las trampas de Rubí de las que un novato debe ser advertido? [cerrado]
Recientemente he aprendido el lenguaje de programación Ruby, y en general es un buen lenguaje. Pero me sorprendió bastante ver que no era tan simple como esperaba. Más precisamente, la" regla de la menor sorpresa " no me pareció muy respetada (por supuesto, esto es bastante subjetivo). Por ejemplo:
x = true and false
puts x # displays true!
Y los famosos:
puts "zero is true!" if 0 # zero is true!
¿Cuáles son las otras "trampas" sobre las que advertirías a un novato de Ruby?
25 answers
Del artículo:
- Los nombres que comienzan con una letra mayúscula se tratan como constantes, por lo que las variables locales deben comenzar con una letra minúscula.
- Los caracteres
$
y@
no indican el tipo de datos variables como en Perl, sino que funcionan como operadores de resolución de alcance. - Para denotar números en coma flotante, se debe seguir con un dígito cero (
99.0
) o una conversión explícita (99.to_f
). Es insuficiente para añadir un punto (99.
), porque los números son susceptibles a la sintaxis del método. - La evaluación booleana de datos no booleanos es estricta:
0
,""
y[]
son todos evaluados atrue
. En C, la expresión0 ? 1 : 0
se evalúa como0
(es decir, false). En Ruby, sin embargo, rinde1
, ya que todos los números evalúan atrue
; solonil
yfalse
evalúan afalse
. Un corolario de esta regla es que los métodos Ruby por convención-por ejemplo, búsquedas de expresiones regulares - devuelven números, cadenas, listas u otros valores no falsos en caso de éxito, peronil
en caso de error (p. ej., desajuste). Esta convención también se usa en Smalltalk, donde solo los objetos especialestrue
yfalse
se pueden usar en una expresión booleana. - Las versiones anteriores a la 1.9 carecen de un tipo de datos de caracteres (en comparación con C, que proporciona el tipo
char
para los caracteres). Esto puede causar sorpresas al cortar cadenas:"abc"[0]
produce97
(un entero, que representa el código ASCII del primer carácter en el string); para obtener"a"
use"abc"[0,1]
(una subcadena de longitud 1) o"abc"[0].chr
. -
La notación
statement until expression
, a diferencia de las declaraciones equivalentes de otros lenguajes (por ejemplo,do { statement } while (not(expression));
en C/C++/...), en realidad nunca ejecuta la sentencia si la expresión ya estrue
. Esto es porquestatement until expression
es en realidad azúcar sintáctica sobreuntil expression statement end
, cuyo equivalente en C / C++ es
while (not(expression)) statement;
al igual questatement if expression
es un equivalente aif expression statement end
Sin embargo, la notación
begin statement end until expression
En Ruby se fact ejecute la sentencia una vez incluso si la expresión ya es verdadera.
- Debido a que las constantes son referencias a objetos, cambiar a lo que una constante se refiere genera una advertencia, pero modificar el objeto en sí no lo hace. Por ejemplo,
Greeting << " world!" if Greeting == "Hello"
no genera un error o una advertencia. Esto es similar a las variablesfinal
en Java, pero Ruby también tiene la funcionalidad de "congelar" un objeto, a diferencia de Java.
Algunas características que difieren notablemente de otras idiomas:
Los operadores usuales para expresiones condicionales,
and
yor
, no siguen las reglas normales de precedencia:and
no enlaza más fuerte queor
. Ruby también tiene operadores de expresión||
y&&
que funcionan como se espera.-
def
insidedef
no hace lo que un programador Python podría esperar:def a_method x = 7 def print_x; puts x end print_x end
Esto da un error acerca de que
x
no está definido. Necesita usar unProc
.
Idioma características
- La omisión de paréntesis alrededor de los argumentos del método puede conducir a resultados inesperados si los métodos toman múltiples parámetros. Los desarrolladores de Ruby han declarado que la omisión de paréntesis en los métodos multiparamétricos puede ser rechazada en futuras versiones de Ruby; el intérprete Ruby actual (noviembre de 2007) lanza una advertencia que anima al escritor a no omitir
()
, para evitar un significado ambiguo del código. No usar()
sigue siendo una práctica común, y puede ser especialmente agradable para utilice Ruby como un lenguaje de programación específico de dominio legible por humanos, junto con el método llamadomethod_missing()
.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-05-07 15:54:34
Los novatos tendrán problemas con métodos de igualdad :
- a == b: comprueba si a y b son iguales. Este es el más útil.
- a.eql? b : también comprueba si a y b son iguales, pero a veces es más estricto (puede comprobar que a y b tienen el mismo tipo, por ejemplo). Se utiliza principalmente en Hashes.
- a. ¿igual? b : comprueba si a y b son el mismo objeto (comprobación de identidad).
- a === b : usado en las declaraciones de caso (lo leo como " a coincide con b ").
Estos ejemplos deberían aclarar los primeros 3 métodos:
a = b = "joe"
a==b # true
a.eql? b # true
a.equal? b # true (a.object_id == b.object_id)
a = "joe"
b = "joe"
a==b # true
a.eql? b # true
a.equal? b # false (a.object_id != b.object_id)
a = 1
b = 1.0
a==b # true
a.eql? b # false (a.class != b.class)
a.equal? b # false
Tenga en cuenta que ==, eql? y igual? siempre debe ser simétrico: si a==b entonces b==a.
También tenga en cuenta que == y eql? se implementan ambos en el Objeto de clase como alias a igual?, así que si crea una nueva clase y desea == y eql? para significar algo más que simple identidad, entonces necesitas anularlos a ambos. Por ejemplo:
class Person
attr_reader name
def == (rhs)
rhs.name == self.name # compare person by their name
end
def eql? (rhs)
self == rhs
end
# never override the equal? method!
end
El === el método se comporta de manera diferente. Primero de todo es no simétrica (a===b ¿ no implica que b===a). Como dije, puedes leer a = = = b como "a coincide con b". He aquí algunos ejemplos:
# === is usually simply an alias for ==
"joe" === "joe" # true
"joe" === "bob" # false
# but ranges match any value they include
(1..10) === 5 # true
(1..10) === 19 # false
(1..10) === (1..10) # false (the range does not include itself)
# arrays just match equal arrays, but they do not match included values!
[1,2,3] === [1,2,3] # true
[1,2,3] === 2 # false
# classes match their instances and instances of derived classes
String === "joe" # true
String === 1.5 # false (1.5 is not a String)
String === String # false (the String class is not itself a String)
La declaración case se basa en === método:
case a
when "joe": puts "1"
when 1.0 : puts "2"
when (1..10), (15..20): puts "3"
else puts "4"
end
Es equivalente a esto:
if "joe" === a
puts "1"
elsif 1.0 === a
puts "2"
elsif (1..10) === a || (15..20) === a
puts "3"
else
puts "4"
end
Si define una nueva clase cuyas instancias representar algún tipo de contenedor o rango (si tiene algo como un include?o una coincidencia? método), entonces usted podría encontrar útil para anular el === método como este:
class Subnet
[...]
def include? (ip_address_or_subnet)
[...]
end
def === (rhs)
self.include? rhs
end
end
case destination_ip
when white_listed_subnet: puts "the ip belongs to the white-listed subnet"
when black_listed_subnet: puts "the ip belongs to the black-listed subnet"
[...]
end
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-25 12:19:45
Monkey patching. Ruby tiene clases abiertas, por lo que su comportamiento se puede cambiar dinámicamente en tiempo de ejecución...
Los objetos podrían responder a métodos indefinidos si
method_missing
osend
ha sido sobrescrito. Esto explota la invocación del método basado en mensajes de Ruby. Rieles' El sistema ActiveRecord usa esto con gran efecto.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-16 22:01:32
El siguiente código me sorprendió. Creo que es una trampa peligrosa: fácil de encontrar y difícil de depurar.
(1..5).each do |number|
comment = " is even" if number%2==0
puts number.to_s + comment.to_s
end
Esto imprime:
1
2 is even
3
4 is even
5
Pero si solo añado comment =
cualquier cosa antes del bloque...
comment = nil
(1..5).each do |number|
comment = " is even" if number%2==0
puts number.to_s + comment.to_s
end
Entonces obtengo:
1
2 is even
3 is even
4 is even
5 is even
Básicamente, cuando una variable solo se define dentro de un bloque, entonces se destruye al final del bloque, y luego se restablece a nil
en cada iteración. Eso es normalmente lo que esperas. Pero si la variable se define antes del bloque, entonces la variable externa se usa dentro del bloque, y su valor es por lo tanto persistente entre iteraciones.
Una solución sería escribir esto en su lugar:
comment = number%2==0 ? " is even" : nil
Creo que mucha gente (incluyéndome) tiende a escribir "a = b if c
" en lugar de "a = (c ? b : nil)
", porque es más legible, pero obviamente tiene efectos secundarios.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-07-13 19:01:00
Cuando se llama a super
sin argumentos, el método sobreescrito se llama realmente con los mismos argumentos que el método sobreescrito.
class A
def hello(name="Dan")
puts "hello #{name}"
end
end
class B < A
def hello(name)
super
end
end
B.new.hello("Bob") #=> "hello Bob"
Para llamar realmente a super
sin argumentos, debe decir super()
.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-17 08:27:14
Los bloques y métodos devuelven el valor de la última línea por defecto. Agregar puts
instrucciones al final para fines de depuración puede causar efectos secundarios desagradables
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-06-11 14:11:25
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-16 21:06:36
Tuve muchos problemas para entender las variables de clase, los atributos de clase y los métodos de clase. Este código podría ayudar a un novato:
class A
@@classvar = "A1"
@classattr = "A2"
def self.showvars
puts "@@classvar => "+@@classvar
puts "@classattr => "+@classattr
end
end
A.showvars
# displays:
# @@classvar => A1
# @classattr => A2
class B < A
@@classvar = "B1"
@classattr = "B2"
end
B.showvars
# displays:
# @@classvar => B1
# @classattr => B2
A.showvars
# displays:
# @@classvar => B1 #Class variables are shared in a class hierarchy!
# @classattr => A2 #Class attributes are not
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-17 10:13:20
Una cosa que aprendí fue a usar el operador ||= con cuidado. y tenga especial cuidado si usted está tratando con booleanos. usualmente usé a / / = b como un catch all para dar a ' a 'un valor por defecto si todo lo demás fallaba y' a ' permanecía nil. pero si a es falso y b es verdadero, entonces a será asignado verdadero.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-18 21:04:31
Los bloques son muy importantes de entender, se usan en todas partes.
No necesita paréntesis alrededor de los parámetros del método. Si los usa o no depende de usted. Algunos dicen que siempre debes usarlas .
Utilice raise y rescue para el manejo de excepciones, no lanzar y atrapar.
Puedes usar
;
pero no tienes que hacerlo a menos que quieras poner varias cosas en una línea.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-10-09 22:17:57
Tuve problemas con los mixins que contienen métodos de instancia y métodos de clase. Este código podría ayudar a un novato:
module Displayable
# instance methods here
def display
puts name
self.class.increment_displays
end
def self.included(base)
# This module method will be called automatically
# after this module is included in a class.
# We want to add the class methods to the class.
base.extend Displayable::ClassMethods
end
module ClassMethods
# class methods here
def number_of_displays
@number_of_displays # this is a class attribute
end
def increment_displays
@number_of_displays += 1
end
def init_displays
@number_of_displays = 0
end
# this module method will be called automatically
# after this module is extended by a class.
# We want to perform some initialization on a
# class attribute.
def self.extended(base)
base.init_displays
end
end
end
class Person
include Displayable
def name; @name; end
def initialize(name); @name=name; end
end
puts Person.number_of_displays # => 0
john = Person.new "John"
john.display # => John
puts Person.number_of_displays # => 1
jack = Person.new "Jack"
jack.display # => Jack
puts Person.number_of_displays # => 2
Al principio, pensé que podría tener módulos con ambos métodos de instancia y métodos de clase simplemente haciendo esto:
module Displayable
def display
puts name
self.class.increment_displays
end
def self.number_of_displays # WRONG!
@number_of_displays
end
[...]
end
Desafortunadamente, method number_of_displays nunca se incluirá o extenderá porque es un "método de clase de módulo". Solo "module instance methods" se puede incluir en una clase (como métodos de instancia) o extendido en una clase (como métodos de clase). Esta es la razón por la que necesitas poner los métodos de instancia de tu mixin en un módulo, y los métodos de clase de tu mixin en otro módulo (normalmente pones los métodos de clase en un submódulo "ClassMethods"). Gracias al método mágico included , puede facilitar la inclusión de métodos de instancia y métodos de clase en una sola llamada "include Displayable" (como se muestra en el ejemplo anterior).
Este mixin contará cada pantalla en un por clase base. El contador es un atributo de clase, por lo que cada clase tendrá su propio (su programa probablemente fallará si deriva una nueva clase de la clase Person ya que el contador @number_of_displays para la clase derivada nunca se inicializará). Es posible que desee reemplazar @number_of_displays por @@number_of_displays para hacer un contador global. En este caso, cada jerarquía de clases tendrá su propio contador. Si quieres un entorno global y único contador, probablemente deberías convertirlo en un atributo de módulo.
Todo esto definitivamente no era intuitivo para mí cuando empecé con Ruby.
Todavía no puedo averiguar cómo hacer limpiamente que algunos de estos métodos mixin sean privados o protegidos (solo el método display y number_of_displays debe incluirse como métodos públicos).
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-17 11:45:25
Preste atención a la notación de rango.
(Al menos, presta más atención que I inicialmente!)
Hay una diferencia entre 0..10
(dos puntos) y 0...10
(tres puntos).
Disfruto mucho de Ruby. Pero esta cosa punto-punto versus punto-punto-punto me molesta. Creo que una "característica" de sintaxis dual tan sutil es:
- fácil de escribir mal, y
- fácil de perder con sus ojos mientras mira sobre el código
No debería ser capaz de causar devastadores errores off-by-one en mis programas.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-06-03 18:23:57
Creo que "and
" y "or
" son guiños a Perl, que es uno de los "padres" más obvios de Ruby (el otro más prominente es Smalltalk). Ambos tienen una precedencia mucho menor (menor que la asignación, de hecho, que es de donde proviene el comportamiento observado) que &&
y ||
que son los operadores que debe usar.
Otras cosas a tener en cuenta que no son inmediatamente obvias:
Realmente no llamas a métodos/funciones, aunque parece que es así. En cambio, como en Smalltalk, se envía un mensaje a un objeto. Así que method_missing
es realmente más como message_not_understood
.
some_object.do_something(args)
Es equivalente a
some_object.send(:do_something, args) # note the :
Los símbolos son muy utilizados. Esas son las cosas que comienzan con :
y no son obvias de inmediato (bueno, no lo eran para mí), pero cuanto antes te familiarices con ellas, mejor.
Ruby es grande en "escribir pato", siguiendo el principio de que "si camina como un pato y grazna como un pato..."que permite la sustitución informal de objetos con un subconjunto común de métodos sin ninguna herencia explícita o relación mixin.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-17 09:31:49
Si declara un setter (también conocido como mutador) usando attr_writer
o attr_accessor
(o def foo=
), tenga cuidado de llamarlo desde dentro de la clase. Dado que las variables se declaran implícitamente, el intérprete siempre tiene que resolver foo = bar
declarando una nueva variable llamada foo, en lugar de llamar al método self.foo=(bar)
.
class Thing
attr_accessor :foo
def initialize
@foo = 1 # this sets @foo to 1
self.foo = 2 # this sets @foo to 2
foo = 3 # this does *not* set @foo
end
end
puts Thing.new.foo #=> 2
Esto también se aplica a los objetos Rails ActiveRecord, que obtienen accesores definidos en función de los campos de la base de datos. Dado que ni siquiera son variables de instancia de estilo@, la forma adecuada de establecer esas los valores individualmente son con self.value = 123
o self['value'] = 123
.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-04-16 18:21:25
Entendiendo la diferencia entre la clase Hora y Fecha. Ambos son diferentes y han creado problemas al usarlos en rails. La clase Time a veces entra en conflicto con otras bibliotecas de clases Time presentes en la biblioteca ruby/rails estándar. Personalmente me tomó mucho tiempo entender lo que estaba pasando exactamente en mi aplicación rails. Más tarde, pensé que cuando lo hice
Time.new
Se refería a una biblioteca en un lugar que ni siquiera conocía.
Lo siento si soy no está claro lo que quiero decir exactamente. Si otros se han enfrentado a problemas similares, por favor vuelva a explicar.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-17 02:31:08
Uno que me ha llamado la atención en el pasado es que la secuencia de escape del carácter de nueva línea (\n
), entre otros, no es compatible con cadenas entre comillas simples. La barra invertida se escapa. Tienes que usar comillas dobles para que el escape funcione como se espera.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-16 20:52:14
x = (true and false) # x is false
0 y " son verdaderas, como usted señaló.
Puede tener un método y un módulo/clase con el mismo nombre (lo cual tiene sentido, porque el método realmente se agrega al Objeto y por lo tanto tiene su propio espacio de nombres).
No hay herencia múltiple, pero con frecuencia los "módulos mixin" se usan para agregar métodos comunes a múltiples clases.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-16 21:46:33
Los métodos pueden ser redefinidos y pueden convertirse en un rascador mental hasta que descubras la causa. (Es cierto que este error es probablemente un poco "más difícil" de detectar cuando la acción de un controlador Ruby on Rails es redefinida por error!)
#demo.rb
class Demo
def hello1
p "Hello from first definition"
end
# ...lots of code here...
# and you forget that you have already defined hello1
def hello1
p "Hello from second definition"
end
end
Demo.new.hello1
Ejecutar:
$ ruby demo.rb
=> "Hello from second definition"
Pero llámelo con las advertencias activadas y puede ver la razón:
$ ruby -w demo.rb
demo.rb:10: warning: method redefined; discarding old hello1
=> "Hello from second definition"
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-04-01 02:52:05
Creo que siempre es bueno utilizar .longitud en las cosas... dado que el tamaño es soportado por casi todo y Ruby tiene tipos dinámicos, puedes obtener resultados muy extraños llamando .tamaño cuando se tiene el tipo equivocado... Preferiría obtener un NoMethodError: undefined method 'length', por lo que generalmente nunca llamo size a objetos en Ruby.
Me mordió más de una vez.
También recuerdo que los objetos tienen id, así que trato de no usar variables call id o object_id solo para evitar confusiones. Si necesito un id en un objeto Users es mejor llamarlo algo como user_id.
Sólo mis dos centavos
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-17 18:57:55
Soy nuevo en ruby, y en mi primera ronda me encontré con un problema con respecto al cambio de flotadores/cadenas a un entero. Comencé con los flotadores y codifiqué todo como f.to_int. Pero cuando continué y usé el mismo método para las cadenas me arrojaron una curva cuando se trataba de ejecutar el programa.
Aparentemente una cadena no tiene un método to_int, pero floats e ints sí.
irb(main):003:0* str_val = '5.0'
=> "5.0"
irb(main):006:0> str_val.to_int
NoMethodError: undefined method `to_int' for "5.0":String
from (irb):6
irb(main):005:0* str_val.to_i
=> 5
irb(main):007:0> float_val = 5.0
=> 5.0
irb(main):008:0> float_val.to_int
=> 5
irb(main):009:0> float_val.to_i
=> 5
irb(main):010:0>
Los paréntesis arbitrarios también me arrojaron al principio. Vi un código con y otro sin. Se me llevó un tiempo darme cuenta de que cualquiera de los estilos son aceptados.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-12-17 10:17:24
Relacionado con la respuesta de monkut, los métodos to_foo
de Ruby indican cuán estricta será la conversión.
Cortos como to_i
, to_s
dile que sea perezoso y conviértelos al tipo de destino incluso si no pueden representarse con precisión en ese formato. Por ejemplo:
"10".to_i == 10
:foo.to_s == "foo"
Las funciones explícitas más largas como to_int
, to_s
significa que el objeto puede representarse de forma nativa como ese tipo de datos. Por ejemplo, la clase Rational
representa todos los números racionales, por lo que puede ser representado directamente como un entero Fixnum (o Bignum) llamando a to_int
.
Rational(20,4).to_int == 5
Si no puede llamar al método longer, significa que el objeto no se puede representar de forma nativa en ese tipo.
Así que básicamente, al convertir, si eres perezoso con los nombres de los métodos, Ruby será perezoso con la conversión.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-02-24 11:54:21
Desde En Ruby ¿por qué no foo = true unless defined?(foo)
hacer la asignación?
foo = true unless defined?(foo) #Leaves foo as nil
Porque foo
se define como nil
cuando se llama defined?(foo)
.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 11:46:33
La iteración sobre los hashes de ruby no está garantizada en ningún orden en particular. (No es un error, es una característica)
Hash#sort
es útil si necesita un pedido en particular.
Pregunta relacionada: ¿Por qué la matriz de Ruby de 1000 pares de clave y valor de hashes siempre está en un orden particular?
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 12:09:36
Este me volvió loco una vez:
1/2 == 0.5 #=> false
1/2 == 0 #=> true
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-07-09 16:39:30
1..5.each {|x| puts x}
No funciona. Tienes que poner el rango entre paréntesis, como
(1..5).each {|x| puts x}
Así que no cree que estés llamando 5.each
. Creo que este es un tema de precedencia, al igual que el x = true and false
gotcha.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-10-09 22:17:16