我有一个元素列表,我需要按此列表类型的某些元素进行分组并将其转换为嵌套集合。这就是我的意思-
考虑以下 -
class StudentA {
private String name;
private int age;
private int subjectId;
private String subjectName;
}
class StudentB {
private String name;
private int age;
List<Subject> subject;
}
class Subject {
private int subjectId;
private String subjectName;
}
我有一个 List<StudentA>
作为我的输入。但是在这个列表中,每个学生都可以有多个科目,因此学生信息是重复的(例如:[new StudentA("A",22,1,"X"), new StudentA("A",22,2,"Y"), new StudentA("B",24,1,"X") ]
等等)。
这不是一个很好的表示,我需要以下格式的数据-
List<StudentB>
请注意,StudentB 将 Subject 列表作为元素。
这是我的想法,但不相信,
- 简单的老式迭代方式,我迭代其中的每个元素 原始列表并构建我需要的内容
- 我也看过 java8 stream api 对收集的数据进行分组,看起来很有希望, 但我似乎无法将列表中的 StudentA 类型转换为我的 学生B型
执行此操作的良好且有效的方法是什么?非常感谢!
最佳答案
如果将 StudentA
的实例分组按名字,你会得到一个 Map<String,List<StudentA>>
.然后您可以流式传输此映射的值并将它们转换为 StudentB
的实例:
List<StudentB> bList =
aList.stream() // Stream<StudentA>
.collect(Collectors.groupingBy(StudentA::getName)) // Map<String,List<StudentA>>
.values() // Collection<List<StudentA>>
.stream() // Stream<List<StudentA>>
.map(list -> {
StudentB b = new StudentB();
b.setName(list.get(0).getName());
b.setAge(list.get(0).getAge());
list.forEach(a -> b.addSubject(new Subject(a.getSubjectID(),a.getSubjectName())));
return b;
}) // Stream<StudentB>
.collect(Collectors.toList());
我冒昧地假设存在一些方法名称和构造函数。
此解决方案的缺点是可能会创建多个 Subject
相同的实例 Subject
.如果您创建 Map<Integer,Subject>
就可以避免这种情况包含 Subject
s 由他们的 ID 索引,并且只创建新的 Subject
s 如果所需的主题 ID 不在 Map
中.
关于java - 将平面列表元素转换为java中的嵌套集合,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47195745/