JRuby:Java 中带有 Ruby 块的命令模式:为什么它有效



我正在学习如何将Java库与Ruby代码集成,并提出了以下问题。

我有一个用 Java 实现的命令模式,如下所示:

public interface Command {
  public String execute(String param);
}
public class CommandRunner {
  public String run(Command cmd, String param) {
    return cmd.execute(param)+" [this is added by run method]";
  }
}

当我将其导入JRuby程序时,我可以实现respond_to? :execute一个参数的Ruby类并将其传递给CommandRunner.new.run。这行得通,这很清楚。

但我也可以这样做:

def put_through_runner(param, &block)
  CommandRunner.new.run block, param
end
p = put_through_runner "through method" do |param|
  "Cmd implementation in block, param: #{param}"
end
puts p

我不是CommandRunner实现execute方法的对象传递给Java,而是传递给它一个代码块,它不实现该方法。它有效:调用块,就好像它是execute方法的实现一样!这怎么可能?JRuby在将块传递给Java时如何处理它?如果我在 Ruby 中实现了CommandRunner,上面的代码将不起作用。

这起作用的原因是称为"闭包转换"的功能(请参阅此处的文档)。 发生的情况是,您传递的块被转换为具有代理的 Proc 对象,该代理为在对象上调用的任何方法调用块中的代码。

最新更新