我是否可以在Java 8中将Clojure函数用作Lambdas?

我在Clojure中使用了许多库来生成符合“ clojure.lang.IFn ”接口的更高阶函数。

它有多个arity重载,即界面看起来像:

public interface IFn extends Callable, Runnable{ public Object invoke() ; public Object invoke(Object arg1) ; public Object invoke(Object arg1, Object arg2) ; public Object invoke(Object arg1, Object arg2, Object arg3) ; .... etc. public Object applyTo(ISeq arglist) ; } 

我能否在Java 8中直接使用这种类型的对象作为可调用的lambda函数?

你是什​​么意思,使用这种类型的对象作为可调用的lambdas?

非常简单的情况下,Java 8 lambdas 可以被认为是语法糖+某些类型接口的匿名类的某种类型推断,即function接口 [1] :

上面使用的接口ActionListener只有一个方法。 许多常见的回调接口都具有此属性,例如Runnable和Comparator。 我们将为只有一个方法的所有接口命名:function接口。

备注:lambdas真的不仅仅是糖; 在内部,它们的实现方式与匿名类不同,并且还存在一些语义差异; 有关此问题的更多信息,请参阅ProgrammersExchange上的这个优秀答案 。 但是,在这个问题和答案的背景下,这并不重要。

在需要某个函数接口的值的任何地方(方法参数,局部变量,字段声明等),可以使用短语法来创建实现此方法的匿名类的实体,即lambda表达式:

 Runnable r = () -> { System.out.println("Hi"); }; // Equivalent to Runnable r = new Runnable() { public void run() { System.out.println("Hi"); } }; public interface Function { T call(F arg); } Function c = s -> ("<" + s + ">").toCharArray(); // Equivalent to Function c = new Function<>() { public char[] call(String s) { return ("<" + s + ">").toCharArray(); } }; 

所以你的问题只能用以下方式解释:是否可以使用Java 8 lambda语法创建IFn类型的对象?

答案是不。 Lambda语法只能通过function接口实现。 clojure.lang.IFn不是一个function界面,因为它包含的不仅仅是单个方法,因此不可能做类似的事情。

 IFn f = (String s) -> s.toLowerCase(); 

不,似乎你不能使用clojure函数,就好像它们也是有效的java lambdas一样。 Clojure的IFn不符合java定义的“lambda”function接口。