Java的Func和Action的等价物

什么是Java的Func和Action的等价物?

我的意思是,而不是写我自己的:

public interface Func<TInput, TResult> { TResult call(TInput target) throws Exception; } public interface Action<T> { void call(T target) throws Exception; } 

在Java 8中,等价物分别是java.util.function.Function<T, R>java.util.function.Consumer<T>接口。 类似地, java.util.function.Predicate<T>等同于System.Predicate<T> 。 如别处所述,这些是接口而不是代表。

相关的一面:我目前主要依靠以下的工具类来做类似LINQ的扩展方法的东西:

 abstract class IterableUtil { public static <T> Iterable<T> where(Iterable<T> items, Predicate<T> predicate) { ArrayList<T> result = new ArrayList<T>(); for (T item : items) { if (predicate.test(item)) { result.add(item); } } return result; } public static <T, R> Iterable<R> select(Iterable<T> items, Function<T, R> func) { ArrayList<R> result = new ArrayList<R>(); for (T item : items) { result.add(func.apply(item)); } return result; } } 

不像System.Linq.Enumerable.Where<TSource>System.Linq.Enumerable.Select<TSource, TResult>我在这里呈现的类似LINQ的方法不是懒惰的,在将结果集合返回给调用者之前完全遍历源集合。 尽pipe如此,我发现它们对于纯粹的语法目的是有用的,如果需要的话可以做成懒惰的。 特定

 class Widget { public String name() { /* ... */ } } 

可以做以下事情:

 List<Widget> widgets = /* ... */; Iterable<Widget> filteredWidgets = IterableUtil.where(widgets, w -> w.name().startsWith("some-prefix")); 

我更喜欢以下内容:

 List<Widget> widgets = /* ... */; List<Widget> filteredWidgets = new ArrayList<Widget>(); for (Widget w : widgets) { if (w.name().startsWith("some-prefix")) { filteredWidgets.add(w); } } 

Callable接口类似于Func。

Runnable接口类似于Action。

一般来说,Java使用匿名内部类来替代C#委托。 例如,这是你如何添加代码来对GUI中的button做出反应:

 button.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { ...//code that reacts to the action... } }); 

重载的Func委托(除了委托vs匿名类问题)的优雅之处在于它们支持0到16个参数( Func<TResult>Func<T, TResult>Func<T1, T2, TResult>等)

不幸的是,由于types擦除,这在Java中是不可能的。 类只能通过genericstypes参数来区分。

Java 8现在BiConsumer了一个名为“ BiConsumer for Action<T, T2>的动物园,因为Java不允许原始types参数BiIntConsumer 。 然而,“动物园”并不是很大,我不知道有一个扩展它的图书馆。 有一个像(int, int) => void这样的函数types文字的奇妙build议,但是没有被采用。

那些真的没有等价物。 你可以用Java创build匿名的内部类,但是往往有特定的接口,而不是像Func和Action这样的通用类。

Java没有委托的概念。 有关解决方法,请参阅Java程序员着眼于C#代表 :

虽然C#有一组与Java类似的function,但它增加了一些新的有趣function。 授权是将方法视为第一类对象的能力。 AC#委托用于Java开发人员使用单一方法的接口。 在本文中,将讨论C#中委托的使用,并为可以执行类似function的Java委托对象提供代码。 在这里下载源代码。

对于Func<T>使用:java.util.function.Supplier http://docs.oracle.com/javase/8/docs/api/java/util/function/Supplier.html