Soy principiante en el lenguaje Ruby, así que traté de imprimir esta línea.
a = 2 z = "A" print a * z
entonces me sale este error
Traceback (most recent call last): 20: from /usr/local/bin/irb:23:in `<main>' 19: from /usr/local/bin/irb:23:in `load' 18: from /var/lib/gems/2.7.0/gems/irb-1.3.7/exe/irb:11:in `<top (required)>' 1: from (irb):24:in `<main>' (irb):24:in `*': String can't be coerced into Integer (TypeError)
Pero cuando traté de usar este código, funcionó correctamente y no recibí ningún error.
puts z * 2 or puts "A" * 2 or z*a HERE I DON'T USE PRINT, PUTS, P
Entonces, ¿por qué recibí el error en el ejemplo inicial y cuál es el mecanismo de acción de dos códigos?
La respuesta corta: el orden importa.
a * z
es básicamente equivalente a a.send(:*, z)
lo que significa que llamas a un *
método en a
y pasas z
como su argumento,
y
z * a
es z.send(:*, a)
lo que significa llamar al método *
en el objeto z
y pasar a
como argumento.
Entonces... si revisa los documentos: https://ruby-doc.org/core-3.0.2/String.html#method-i-2El método *
de una cadena espera int como argumento, y
https://ruby-doc.org/core-2.5.0/Integer.html#method-i-2A int's *
espera que se pase un valor numérico (int o float) como argumento.
O, para decirlo de otra manera, * (y +,-, etc.) no son operadores en Ruby (como lo son en C u otros lenguajes) pero son lo que se llama un azúcar sintáctico para hacer su vida más fácil, pero están en métodos de hecho sobre los objetos.
Cambié los nombres de las variables para representar sus tipos y simplificar la explicación.
string = 'A' # from z = 'A' integer = 2 # from a = 2
A continuación, identifiquemos qué hace el operador *
( método ):
# string * integer -> new_string # returns a new `String` containing `integer` copies of the receiver. puts string * integer # repeat A twice # "AA"
En lo anterior, una cadena responde a *
y acepta un argumento entero. Los otros ejemplos realizan una multiplicación:
# integer * integer -> numeric_result # performs multiplication puts integer * 2 # multiply 2 by 2 # 4
Entonces, ¿por qué recibí el error en el ejemplo inicial?
Porque el operador/método de cadena *
requiere un argumento entero .
AQUÍ NO UTILIZO PRINT, PONE, P
print
, puts
y p
simplemente muestran el resultado de la operación o una declaración, simplemente se comportan de manera diferente. Todavía puede ver el resultado sin usarlos (en la consola IRB o Rails)
'A' * 2 # => 'AA' 2 * 2 # => 4