如何在Ruby中动态打开方法

我想动态打开一个方法并根据输入字段返回一个值。 我试着用这里的例子来问我想要什么。 如果我能成功这个例子,我会做我想做的事。

假设我有一个名为Greetings的类,它有一个名为greet()的方法,它将消息作为参数。

class Greetings def self.greet(message) return "good morning" if message=="gm" return "evening" if message=="ge" return "good afternoon" if message=="ga" end end 

当我做Greetings.greet("ge") ,我得到“晚上”作为输出。 我想改变这种行为而不改变上面的Greetings类(显而易见的原因是它是一个外部库)。

我的问题很简单。 当我打电话给Greetings.greet("ge")时,我应该怎么做才能给我回复“A Very Good Evening”,对于所有其他输入,它应该返回原始类返回的内容。 我知道在Ruby中动态打开一个类但是如何将该方法委托给其他情况的父类?

我会在config / initializers文件夹中写这个,因为我正在使用Rails。

方法别名

例如,您可以将旧方法别名为old_greet ,并使用您自己的方法重新定义:

 class Greetings class << self alias_method :old_greet, :greet def greet(message) (message == "ge") ? "A Very Good Evening" : old_greet(message) end end end 

然后你可以:

 puts Greetings.greet("ge") 

方法链

使用Rails alias_method_chainfunction:

 class Greetings class << self def greet_with_modifications(message) (message == "ge") ? "A Very Good Evening" : greet_without_modifications(message) end alias_method_chain :greet, :modifications end end 

然后你可以:

 puts Greetings.greet("ge") 

扩展课程

您可以创建自己的类,扩展原始类,如下所示:

 module My class Greetings < ::Greetings def self.greet(message) case message when "ge" "A Very Good Evening" else super(message) end end end end 

然后你可以:

 puts My::Greetings.greet("ge") 

你可以做这样的事情来重新打开代码中的类:

 Greetings.class_eval do class << self alias :old_greet :greet end def self.greet(message) return "a very good evening" if message == "ge" old_greet(message) end end 

你可以做点什么

 class Greetings class << self alias :old_greet :greet end def self.greet(message) return "A very good evening" if message == 'ge' old_greet(message) end end 

那简单来说呢?

 class Greetings def self.greet(message) return "good morning" if message=="gm" return "evening" if message=="ge" return "good afternoon" if message=="ga" end end class GreetingsOverloaded < Greetings def self.greet(message) return "A Very Good Evenin" if message=="ge" super end end puts Greetings.greet("ge") puts GreetingsOverloaded.greet("ge")