java - 在消费者方法中创建的 Lambda Collect 元素

标签 java lambda java-8 java-stream

我正在从丑陋的嵌套 for 循环转变为 java 中设计精美的 lambda 表达式。

这是我的实际代码

for (String foo : foos) {
    for (Bar bar : bars) {    
        if (bar.getFoo().equals(foo)) {
            FooBar fooBar = new FooBar();                           
            fooBar.setBar(bar);
            listOfFooBar.add(fooBar);
            break;
        }
    }
}

我实际的 lambda 代码来替换上面的代码

foos.forEach(i -> bars.stream().filter(p -> p.getFoo().equals(i)).findFirst().ifPresent(p -> {
        FooBar s = new FooBar();
        fooBar.setBar(bar);
        listOfFooBar.add(fooBar);
    }));

我的问题是,有没有办法用某种 collect() 方法填充 listOfFooBar

类似listOfFooBar = foos.forEach(.....).collect(Collectors.toList());

一个事实是,bars 将始终包含每个 foo,foos 基本上是 bars 的一小部分。

如果有更好的方法(在性能或优雅方面)来执行该 lambda,请分享。

最佳答案

由于每个 Foo 只有一个 Bar,您可以从创建一个将 Foos 链接到 Bars 的 map 开始:

Map<String, Bar> barsByFoo = bars.stream().collect(toMap(Bar::getFoo, b -> b));

如果 bars 比 foos 多很多,你可以过滤:

Map<String, Bar> barsByFoo = bars.stream()
                                 .filter(b -> foos.contains(b.getFoo()))
                                 .collect(toMap(Bar::getFoo, b -> b));

然后可以编写嵌套的 for 循环:

List<FooBar> listOfFooBar = foos.stream()
        .map(barsByFoo::get)
        .filter(Objects::nonNull)
        .map(FooBar::new)
        .collect(toList());

这假设有一个 FooBar(Bar)构造函数。

或者您可以从另一侧解决问题并使用(我认为)等效算法(在这种情况下您可能会受益于使用 Set<Foo>):

List<FooBar> listOfFooBar = bars.stream()
        .filter(bar -> foos.contains(bar.getFoo()))
        .map(FooBar::new)
        .collect(toList());

无论哪种方式,它通常都有助于退出初始循环,因为不同的算法/方法通常有利于干净的 lambda 解决方案。

关于java - 在消费者方法中创建的 Lambda Collect 元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32632155/

相关文章:

java - 如何在 Kotlin 编写的接口(interface)中使用默认方法的 Java 8 功能

java - 如何删除 uri 路径信息?

java - 在 Java 中将(16 进制)字节数组转换为字符串

c# - 搜索层次列表

lambda - java8中的lambda有默认变量占位符吗?

java - 当一个类实现两个具有相同方法签名但修饰符 default 和 static 不同的接口(interface)时会发生什么

java - Android Studio : Adding a new java file to an existing package - "Unresolved Reference"

java - 从映射信息中打印出姓名

python - 从 lambda 连接到 Redshift 并使用 python 获取一些记录

c++ - C++ 中 lambda 和常规函数的不同堆栈深度?