按谓词拆分Java列表,并为每个子列表映射不同的函数
我需要一个相当普通的任务的帮助,但我不能清楚地做好它 我有:整数列表 我想要的是:按谓词将数组拆分为两个,并为每个数组应用不同的函数 例如,我丑陋的解决方案:按谓词拆分Java列表,并为每个子列表映射不同的函数,java,collections,Java,Collections,我需要一个相当普通的任务的帮助,但我不能清楚地做好它 我有:整数列表 我想要的是:按谓词将数组拆分为两个,并为每个数组应用不同的函数 例如,我丑陋的解决方案: Map<Boolean, List<Integer>> collect = Stream.of(1, 2, 3, 4, 5, 6, 7, 8, 9) .collect(Collectors.<Integer>partitioningBy(e ->
Map<Boolean, List<Integer>> collect =
Stream.of(1, 2, 3, 4, 5, 6, 7, 8, 9)
.collect(Collectors.<Integer>partitioningBy(e -> e % 2 == 0));
List<Integer> result = collect.get(true)
.stream()
.map(x -> x * x)
.collect(Collectors.toList());
result.addAll(collect.get(false)
.stream()
.map(x -> x + 2)
.collect(Collectors.toList()));
System.out.println(result);
Map collect=
(1,2,3,4,5,6,7,8,9)流
.collect(收集器.partitionBy(e->e%2==0));
列表结果=collect.get(true)
.stream()
.map(x->x*x)
.collect(Collectors.toList());
result.addAll(collect.get)(false)
.stream()
.map(x->x+2)
.collect(Collectors.toList());
系统输出打印项次(结果);
但我认为这个任务可以用FP的方式解决,使用收集器,但不知道如何解决。
是的,我只能使用Java8,没有第三方库,比如Guava/ApacheCommons等等
希望你能帮助我,教我新的方法
谢谢,对不起我的英语 您可以改用groupingBy:
Map<Boolean, List<Integer>> grouped = Stream.of(1, 2, 3, 4, 5, 6, 7, 8, 9)
.collect(Collectors.groupingBy(e -> e % 2 == 0));
System.out.println("" + grouped);
然后根据需要处理映射。如果不需要更改输入
流的顺序,则可以跳过分区:
List<Integer> result =
Stream.of(1, 2, 3, 4, 5, 6, 7, 8, 9)
.map(x -> x % 2 == 0 ? x * x : x + 2)
.collect(Collectors.toList());
如果要对分区进行分组,可以使用自定义的收集器
:
List<Integer> result =
Stream.of(1, 2, 3, 4, 5, 6, 7, 8, 9)
.collect(Collector.of (
() -> {
Map<Boolean,List<Integer>> map = new HashMap<>();
map.put (true, new ArrayList<> ());
map.put (false, new ArrayList<> ());
return map;
},
(m,i) -> {
if (i % 2 == 0)
m.get (true).add(i*i);
else
m.get (false).add(i+2);
},
(b1,b2)-> {
b1.putAll (b2);
return b1;
},
m -> {
List<Integer> l = m.get(true);
l.addAll (m.get(false));
return l;
}));
您需要输出列表首先包含第一个分区的所有元素,然后包含第二个分区的所有元素,还是可以保持输入列表的原始顺序?最好保持原始列表的顺序。您的“丑陋”解决方案实际上是一个直截了当的解决方案。您应该记住,收集器并不保证列表是可变的。如果使用Collectors.partitioning by(e->e%2==0,Collectors.toCollection(ArrayList::new))
可以像List result=collect.get(true)那样进行后期处理;结果.replaceAll(x->x*x);collect.get(false).replaceAll(x->x+2);result.addAll(collect.get(false))代码>它与我的解决方案有何不同?在这两种情况下,我都需要编写smth,比如:List result=collect.get(true).stream().map(x->x*x).collect(Collectors.toList());addAll(collect.get(false).stream().map(x->x+2).collect(collector.toList());此时,您可以对映射条目进行流式处理(例如使用.forEach()),并根据key vaue.bulky solution处理这些条目!如果顺序不重要,你会怎么写?@aarexer我也回答了。请参阅答案的顶部。根据第一个变量,您可以使用List result=Stream.of(1,2,3,4,5,6,7,8,9)。排序(Comparator.comparingit(x->x%2)).map(x->x%2==0?x*x:x+2)。collect(collector.toList())代码>如果需要更改订单。@霍尔格:好主意
[3, 4, 5, 16, 7, 36, 9, 64, 11]
List<Integer> result =
Stream.of(1, 2, 3, 4, 5, 6, 7, 8, 9)
.collect(Collector.of (
() -> {
Map<Boolean,List<Integer>> map = new HashMap<>();
map.put (true, new ArrayList<> ());
map.put (false, new ArrayList<> ());
return map;
},
(m,i) -> {
if (i % 2 == 0)
m.get (true).add(i*i);
else
m.get (false).add(i+2);
},
(b1,b2)-> {
b1.putAll (b2);
return b1;
},
m -> {
List<Integer> l = m.get(true);
l.addAll (m.get(false));
return l;
}));
[4, 16, 36, 64, 3, 5, 7, 9, 11]