是否可以使用块定义一个Ruby单例方法? [英] Is it possible to define a Ruby singleton method using a block?

查看:196
本文介绍了是否可以使用块定义一个Ruby单例方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以,我想为一个对象定义一个singleton方法,但我想使用一个闭包。



例如,

  def define_say(obj,msg)
def obj.say
puts msg
end
end

o = Object.new
define_say o,hello world!
o.say

这不起作用,因为通过def定义了一个单例方法,不是一个闭包,所以我得到一个异常,msg是一个未定义的变量或方法。



我想做的就像使用define_method方法在Module类中,但是据我所知,这只能用于在类上定义一个方法...但我想要一个Singleton方法...



所以,我想写这样的东西:

  def define_say(obj,msg)
obj.define_singleton_method(:say){
puts msg
}
end

有没有人知道我可以如何实现这一点,而无需创建一个方法来存储一个Proc,然后在单一方法中使用Proc? (基本上,我想要一个干净,非黑客的方式这样做)

解决方案

这里有一个答案,寻找

  def define_say(obj,msg)
#获取obj的singleton类的句柄
metaclass = class<< obj;自; end

#添加使用define_method而不是def x.say的方法,所以我们可以使用闭包
metaclass.send:define_method,:say do
puts msg
end
end

使用(从IRB粘贴)

 >> s =my string
=> my string
>> define_say(s,I am S)
=> #< Proc:0xb6ed55b0 @(irb):11>
>> s.say
我是S
=> nil

有关更多信息(和一个小图书馆, >

http://viewsourcecode.org/why/ hacking / viewingMetaclassesClearly.html



另外,如果你是一个红宝石程序员,而你还没有读过,现在就去吧!


So, I want to define a singleton method for an object, but I want to do it using a closure.

For example,

def define_say(obj, msg)
  def obj.say
    puts msg
  end
end

o = Object.new
define_say o, "hello world!"
o.say

This doesn't work because defining a singleton method via "def" is not a closure, so I get an exception that "msg" is an undefined variable or method.

What I would like to do is something like using the "define_method" method in the Module class, but as far as I can tell, this can only be used to define a method on a class... but I want a Singleton Method...

So, I would love to write it something like this:

def define_say(obj, msg)
  obj.define_singleton_method(:say) {
    puts msg
  }
end

Does anyone know how I can achieve this without having to create a method to store a Proc and then use the Proc within a singleton method? (basically, I want a clean, non-hacky way of doing this)

解决方案

Here's an answer which does what you're looking for

def define_say(obj, msg)
  # Get a handle to the singleton class of obj
  metaclass = class << obj; self; end 

  # add the method using define_method instead of def x.say so we can use a closure
  metaclass.send :define_method, :say do
    puts msg
  end
end

Usage (paste from IRB)

>> s = "my string"
=> "my string"
>> define_say(s, "I am S")
=> #<Proc:0xb6ed55b0@(irb):11>
>> s.say
I am S
=> nil

For more info (and a little library which makes it less messy) read this:

http://viewsourcecode.org/why/hacking/seeingMetaclassesClearly.html

As an aside, If you're a ruby programmer, and you HAVEN'T read that, go do it now~!

这篇关于是否可以使用块定义一个Ruby单例方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆