【问题标题】:Usage of function type congruent lambda expressions in Java 8Java 8 中函数类型全等 lambda 表达式的使用
【发布时间】:2014-11-11 10:37:42
【问题描述】:

我对

的定义和用法感到困惑
Stream.collect(Supplier<R> supplier, BiConsumer<R,? super T> accumulator, BiConsumer<R,R> combiner)

method 在 Java 8 中。

方法签名包括BiConsumer 类型参数。 BiConsumer 功能接口定义了一种功能方法accept(Object, Object)。据我了解,我现在可以将 congruent 的任何 lambda 表达式用于此功能接口。

但 Stream.collect JavaDoc 中提到的示例是例如

 List<String> asList = stringStream.collect(ArrayList::new, ArrayList::add, ArrayList::addAll);

我不明白为什么ArrayList.add(E e)(单参数)与BiConsumer.accept(T t, U u)方法(两个参数)一致,并且可以作为collect方法中的累加器函数。

如您所见,我显然缺乏理解并感谢任何解释。

【问题讨论】:

标签: java lambda java-8


【解决方案1】:

累加器 BiConsumer 的两个参数是 (1) 列表本身和 (2) 要添加到其中的项目。这个:

List<String> asList = stringStream.collect(
    ArrayList::new,
    ArrayList::add,
    ArrayList::addAll
);

等价于:

List<String> asList = stringStream.collect(
    () -> new ArrayList<>(),
    (list, item) -> list.add(item),
    (list1, list2) -> list1.addAll(list2)
);

这将给出与此相同的结果:

List<String> asList = stringStream.collect(
    new Supplier<ArrayList<String>>() {
        @Override
        public ArrayList<String> get() {
            return new ArrayList<>();
        }
    },

    new BiConsumer<ArrayList<String>,String>() {
        @Override
        public void accept(ArrayList<String> list, String item) {
            list.add(item);
        }
    },

    new BiConsumer<ArrayList<String>,ArrayList<String>>() {
        @Override
        public void accept(ArrayList<String> list1, ArrayList<String> list2) {
            list1.addAll(list2);
        }
    }
);

【讨论】:

  • 与@Misha 的回答一样正确,但更详细 - 因此被接受
【解决方案2】:

ArrayList::add 实际上有 2 个参数。您在其上调用add 方法的ArrayList 对象和add 的参数。

ArrayList::add 等价于(list, element) -&gt; list.add(element),因此它作为BiConsumer 工作

【讨论】:

    猜你喜欢
    • 2014-12-14
    • 1970-01-01
    • 1970-01-01
    • 2017-11-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-03-20
    • 2015-06-01
    相关资源
    最近更新 更多