【问题标题】:Performance difference between Stream.map and Collectors.mapping [duplicate]Stream.map 和 Collectors.mapping 之间的性能差异 [重复]
【发布时间】:2020-02-11 19:33:44
【问题描述】:

上次我发现 Java 8 及更高版本的函数式编程的角落时,我在 Collectors 类中发现了一个静态方法 mapping

我们有一个 Employee 类,例如:

@AllArgsConstructor
@Builder
@Getter
public class Employee {
  private String name;
  private Integer age;
  private Double salary;
}

假设我们有一个Employee 类的 POJO 列表,我们想要接收所有员工姓名的列表。我们有两种方法喜欢:

    List<Employee> employeeList
        = Arrays.asList(new Employee("Tom Jones", 45, 15000.00),
        new Employee("Harry Andrews", 45, 7000.00),
        new Employee("Ethan Hardy", 65, 8000.00),
        new Employee("Nancy Smith", 22, 10000.00),
        new Employee("Deborah Sprightly", 29, 9000.00));

    //IntelliJ suggest replacing the first approach with ```map``` and ```collect```

    List<String> collect =
        employeeList
        .stream()
        .collect(
            Collectors.mapping(Employee::getName, Collectors.toList()));

    List<String> collect1 =
        employeeList
            .stream()
            .map(Employee::getName)
            .collect(Collectors.toList());

我知道第一种方法在Stream 上使用终端操作,在Stream 上使用第二种中间操作,但我想知道第一种方法的性能是否比第二种方法更差,反之亦然。如果您能解释第一种情况下我们的数据源(employeeList)的大小将显着增加时潜在的性能下降,我将不胜感激。

编辑:

我创建了一个简单的两个测试用例,它们由在一个简单的 for 循环中生成的记录提供。因此,对于小数据输入,使用Stream.mapCollectors.mapping 的传统方法之间的差异很小。另一方面,在我们大量增加30000000 等数据数量的情况下,令人惊讶的是,Collectors.mapping 开始工作得更好一些。为了不让数据输入空手而归30000000 Collectors.mapping 持续56 seconds 作为@RepeatedTest 进行10 次迭代,并且对于相同的迭代使用相同的数据输入更容易识别的方法,例如Stream.map 然后collect最后5 second longer。我知道我的临时测试不是最好的,并且由于 JVM 优化它无法说明现实,但我们可以声称对于大量数据输入Collectors.mapping 可能更可取。反正我觉得这个

【问题讨论】:

  • 看看this post,这是一个类似的问题。种类繁多,经验数据和指向更多同类帖子的链接。对于由此产生的基线论点,存在差异,但它们并不重要。
  • @Naman 我看过这篇文章,但这个问题回答了一个问题,为什么我们需要mapping 和类似的方法来简化我们流上的收集操作。
  • 我将引用安迪的回答 我怀疑是否存在有意义的性能差异。 您必须根据自己的数据对其进行基准测试才能确定。

标签: java functional-programming java-stream collectors


【解决方案1】:

我怀疑是否存在有意义的性能差异。您必须根据您的数据对其进行基准测试才能确定。

请注意,mapping 实际上并不是直接用作收集器,而是用作另一个收集器中的下游收集器:

mapping() 收集器在用于多级归约时最有用,例如 groupingBy 或 partitioningBy 的下游。

Effective Java 第 3 版中也有关于此的内容(在第 46 条中,大约在第 214 页的 2/3 处,开头的段落“counting 方法返回的收集器”)。基本上,它说不要在你在这里做的第一种方式中使用像 mapping 这样的东西。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-07-23
    • 1970-01-01
    • 2019-09-16
    • 1970-01-01
    • 2010-11-21
    • 2012-05-26
    相关资源
    最近更新 更多