【发布时间】:2015-06-01 22:36:59
【问题描述】:
我可以使用 TracePoint API 访问 Ruby 方法的参数:
def foo(foo_arg)
end
trace = TracePoint.trace(:call, :c_call) do |tp|
tp.disable
case tp.method_id
when :foo, :sub
method = eval("method(:#{tp.method_id})", tp.binding)
method.parameters.each do |p|
puts "#{p.last}: #{tp.binding.local_variable_get(p.last)}"
end
end
tp.enable
end
trace.enable
foo(10)
# => foo_arg: 10
但是,当我尝试使用 c 方法调用时,我得到了一个错误。
"foo".sub(/(f)/) { $1.upcase }
script.rb:20:in `method': undefined method `sub' for class `Object' (NameError)
from script.rb:20:in `<main>'
from script.rb:8:in `eval'
from script.rb:8:in `block in <main>'
from script.rb:20:in `<main>'
这看起来是因为使用 C 方法调用和常规 Ruby 方法调用时返回的绑定之间存在差异。
在 Ruby 情况下 tp.self 等于 tp.binding.eval("self") 是 main 但是在 C 情况下 tp.self 是 "foo" 和 tp.binding.eval("self") 是 main。对于 Ruby 和 C 定义的方法,有没有办法使用 TracePoint 将参数传递给方法?
【问题讨论】:
标签: ruby metaprogramming