gpt4 book ai didi

java - 如何使用Stream过滤嵌套对象?

转载 作者:行者123 更新时间:2023-11-30 02:02:43 26 4
gpt4 key购买 nike

我想使用 Stream API 过滤嵌套对象。问题是有太多的嵌套类,并且使用下面的方法我编写了太多重复的代码。

有没有办法在不重复代码的情况下处理这个流?

public class Country{
Map<String, City> cities;
}

public class City{
Map<String, School> schools;
}

public class School{
String name;
String address;
Model model;
}

public class Model{
String name;
Teacher teacher;
}

public class Teacher{
String name;
String id;
}

我的直播;

country.getCities().values().stream().foreach(
(City city) ->
city.getSchools()
.entrySet()
.stream()
.filter(schoolEntry -> schoolEntry.getValue().getName().equals("test"))
.filter(schoolEntry -> schoolEntry.getValue().getModel().getName().equals("test2"))
.filter(schoolEntry -> schoolEntry.getValue().getModel().getTeacher().getName().equals("test2"))
.foreach(schoolEntry -> {
String schoolKey = schoolEntry.getKey();
resultList.put(schoolKey, schoolEntry.getValue().getModel().getTeacher().getId());
})
);

最佳答案

您可以定义一个方法来将其用作 Predicate过滤学校。

public static boolean matches(School school, String schoolName, String modelName, String teacherId) {
return school.getName().equals(schoolName)
&& school.getModel().getName().equals(modelName)
&& school.getModel().getTeacher().getId().equals(teacherId);
}

将其应用于流:

public static Map<String, String> getSchoolAndTeacherFrom(Country country, Predicate<School> schoolWithModelAndTeacher) {
return country.getCities().values().stream()
.flatMap(c -> c.getSchools().entrySet().stream())
.filter(s -> schoolWithModelAndTeacher.test(s.getValue()))
.collect(Collectors.toMap(Entry::getKey, schoolEntry -> schoolEntry.getValue().getModel().getTeacher().getId()));
}

像这样使用:

    Country country = <county>
Predicate<School> schoolWithModelAndTeacher = school -> matches(school, "test1", "test2", "test2");
getSchoolAndTeacherFrom(country, schoolWithModelAndTeacher);

一些进一步的想法:

如果 map schools使用School.getName()作为键,那么我们可以写:

public static Map<String, String> getSchoolAndTeacherFrom(Country country, Predicate<School> schoolWithModelAndTeacher) {
return country.getCities().values().stream()
.flatMap(city -> city.getSchools().values().stream())
.filter(schoolWithModelAndTeacher::test)
.collect(Collectors.toMap(School::getName, school -> school.getModel().getTeacher().getId()));
}

假设一个国家/地区的学校名称和教师 ID 是唯一的(而模型名称很常见),则过滤结果将是单个值(如果有)。但那就不需要 Map作为结果类型。类型为 Entry<String String> 的结果会做到的。
如果谓词的参数仍然已知(学校、模型、教师),那么整个问题只是一个问题:在某个国家的给定学校中是否存在给定模型的给定教师。那么我们可以把它写得更短:

public static boolean isMatchingSchoolInCountryPresent(Country country, Predicate<School> schoolWithModelAndTeacher) {
return country.getCities().values().stream()
.flatMap(c -> c.getSchools().values().stream())
.anyMatch(schoolWithModelAndTeacher::test);
}

关于java - 如何使用Stream过滤嵌套对象?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52308856/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com