【发布时间】:2016-08-25 02:33:44
【问题描述】:
我有一个包含许多重复对象和一些需要合并的字段的对象列表。我想将其简化为仅使用 Java 8 Streams 的唯一对象列表(我知道如何通过老式方法做到这一点,但这是一个实验。)
这就是我现在所拥有的。我不太喜欢这样,因为地图构建似乎无关紧要,而 values() 集合是支持地图的视图,您需要将其包装在新的 ArrayList<>(...) 中以获得更具体的集合。有没有更好的方法,也许使用更通用的归约操作?
@Test
public void reduce() {
Collection<Foo> foos = Stream.of("foo", "bar", "baz")
.flatMap(this::getfoos)
.collect(Collectors.toMap(f -> f.name, f -> f, (l, r) -> {
l.ids.addAll(r.ids);
return l;
})).values();
assertEquals(3, foos.size());
foos.forEach(f -> assertEquals(10, f.ids.size()));
}
private Stream<Foo> getfoos(String n) {
return IntStream.range(0,10).mapToObj(i -> new Foo(n, i));
}
public static class Foo {
private String name;
private List<Integer> ids = new ArrayList<>();
public Foo(String n, int i) {
name = n;
ids.add(i);
}
}
【问题讨论】:
-
是否可以在不使用中间映射的情况下实现这个“old skool”(通常不使用 lambda/streams)?我认为,由于重复可能出现在输入中的任何地方,它们都必须在某个地方缓冲,直到所有输入都被处理完。