这个问题很简单,可以用数千种方法解决。但是由于我正在学习Java 8,所以我想以Java 8的方式来做。
我有两个字符串列表,例如:
List<String> list1 = Arrays.asList("A", "B", "C", "D");
List<String> list2 = Arrays.asList("A", "D", "E");
我想从list1
中获取第一个元素,并检查字符串是否存在于list2
中并产生一个Map<Boolean, String>
。像这样:
Map<Boolean, String> resultMap = list1.stream().collect(partial -> Collectors.partitioningBy(list2.stream().filter(existing -> matchString(partial, existing))));
private static boolean matchString(String partial, String existing) {
return partial.equals(existing);
}
以上代码在matchString(partial, existing)
处出现编译错误:
第一个参数类型错误。找到:“”,必填: 'java.lang.String'
要注意的是,在我的实际情况中,它不是简单的字符串列表,而是更复杂的对象,并且该对象不会覆盖equals
或hashcode
方法。
我非常知道这可以通过不同的方式来完成。但是有人可以让我知道在这种特定情况下如何使用Collectors.partitioningBy
。
答案 0 :(得分:3)
使用Collectors.partitioningBy
,您可以获得Map<Boolean, List<String>>
。来自partitioningBy
文档:
返回一个收集器,该收集器根据
Predicate
对输入元素进行分区,并将其组织为Map<Boolean, List<T>>
。
在您的情况下:
Map<Boolean, List<String>> map = list1.stream()
.collect(Collectors.partitioningBy(list2::contains));
如果没有覆盖equals
/ hashcode
的更复杂的对象,则可以按某些特定字段进行比较。假设您有类似的东西:
class ComplexObj {
private String id;
...
}
Map<Boolean, List<ComplexObj>> map = list1.stream()
.collect(Collectors.partitioningBy(obj -> list2.stream()
.map(ComplexObj::getId)
.anyMatch(id -> id.equals(obj.getId()))));
答案 1 :(得分:1)
使用Collectors.partitioningBy在下面找到我的实现。我使用List.contains()方法作为谓词,并且效果很好。请尝试并分享反馈/建议。谢谢。
package net.javapedia.streams;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;
public class PartitioningByEx1 {
public static void main(String[] args) {
List<String> list1 = Arrays.asList("A", "B", "C", "D");
List<String> list2 = Arrays.asList("A", "D", "E");
list1.stream().collect(Collectors.partitioningBy(item -> list2.contains(item)))
.forEach((key, val) -> System.out.println(key + "-->>" + val));
}
}
程序输出: