Aquí es una explicación:
De ruby docs.
Un módulo es una colección de métodos y constantes. Los métodos en un módulo pueden ser métodos de instancia o métodos de módulo. Los métodos de instancia aparecen como métodos en una clase cuando se incluye el módulo, los métodos de módulo no. Por el contrario, se pueden llamar a los métodos de módulo sin crear un objeto de encapsulado, mientras que los métodos de instancia pueden no serlo. (Véase el módulo # module_function.)
self.methodname
dentro de un módulo crea un método módulo.
En este caso, cuando invoca M::helper
, realmente hace M.helper
cuando lo mira desde el punto de vista de un desarrollador C++. El receptor es el objeto Módulo (una instancia del módulo tipo ruby incorporado) en este caso.
Otra manera de mirar esto es para entender un concepto receptor, cada llamada al método consiste en un nombre del receptor y el método (+ params opcionalmente y el bloque de código). El receptor puede ser Module object
, Class object
o instancia de una clase definida por el usuario.
Solo puede invocar métodos de módulo (o clase) en un objeto de módulo (o clase). Puede invocar cualquier método (Módulo/Clase/instancia) en una instancia.
Si desea invocar un método de instancia definido en un módulo, debe darle un receptor por including
ese módulo en alguna clase y crear una instancia de este.
Así que en este caso otra solución puede ser:
module MM
def helper(param)
puts "hello #{param}"
end
class ReceiverClass
include MM # add helper() to ReceiverClass
end
class C < Struct.new(:param)
def work
ReceiverClass.new.helper(param)
end
end
end
c = MM::C.new("world")
c.work
gracias por la explicación de la diferencia entre usar uno mismo. e incluyendo el módulo. –