【发布时间】:2019-12-26 04:57:18
【问题描述】:
关于员工的表包含以下数据:员工 ID、员工姓名、经理 ID 和团队成员 ID。每个员工都会根据他们的团队规模有多个条目。假设团队中有 5 名其他成员的员工将有五行,其中员工和经理 ID 重复,每行重复一个团队成员的 ID。
示例表:
employeeId | employeeName | managerId | teamEmployeeId |
-------------------------------------------------------
1000 | Alex | 4000 | 1101 |
1200 | Bran | 4100 | 1301 |
1200 | Bran | 4100 | 1302 |
1000 | Alex | 4000 | 1102 |
1200 | Bran | 4100 | 1303 |
1000 | Alex | 4000 | 1103 |
1200 | Bran | 4100 | 1304 |
1200 | Bran | 4100 | 1305 |
1000 | Alex | 4000 | 1104 |
目标是将每个员工的团队 ID(也包括经理 ID)拆分为单独的数组以供以后使用。
预期结果:
allIds:
1000
1200
teamIds for "Alex" :
1101
1102
1103
1104
4000
teamIds for "Bran" :
1301
1302
1303
1304
1305
4100
获取唯一员工 ID 的第一部分正在运行(基于此 answer)。但是尝试使用员工 ID 拆分团队成员会返回第一个值,但次数正确。说:一个有 5 人的团队返回一个由 5 人组成的数组,其中包含第一个成员的 id。没有添加经理的 ID。
我正在使用的代码:
List<ViewData> list = getDataList();
String[] allIds = list.parallelStream()
.map(ViewData::getId).distinct().toArray(String[]::new);
System.out.println(allIds.length + "\n");
for (String id : allIds) {
String[] teamIds = list.parallelStream()
.filter(row -> row.getId().equals(id))
.map(ViewData::getTeamId).distinct()
.toArray(String[]::new);
teamIds = Arrays.copyOf(teamIds, teamIds.length+1 );
teamIds[teamIds.length] = list.parallelStream()
.filter(obj -> obj.getId().equals(id))
.map(ViewData::getManagerId).toString();
System.out.println(teamIds.length + "\n");
}
我知道这是一个逻辑错误。我为 filter() 引用的所有文档都显示语法是正确的。我的理解是 filter() 返回其 id 与我正在循环的那一行匹配的整行,而 map() 从该行中取出团队成员的 id,最后所有内容都作为字符串数组返回。
我哪里做错了?编写代码或了解这些函数的工作原理?
编辑:
如果这样的表导致重复/重复行(尤其是它应该存在的确切时间):
没有主键的视图(即,没有保证唯一的列)需要一个复合主键,该主键是通过组合两个唯一的列来派生的。
为复合键组合创建单独的
@Embeddable类将其添加到主模型类:
@EmbeddedId private UniqueId uniqueId;按照答案中的现有逻辑继续:
for (String id : allIds) {
String[] teamIds = list.stream()
.filter(row -> row.getUniqueId().getId().equals(id))
.map(obj -> obj.getUniqueId().getTeamEmployeeId())
.toArray(String[]::new);
teamIds = Arrays.copyOf(teamIds, teamIds.length + 1);
teamIds[teamIds.length - 1] = list.stream()
.filter(obj -> obj.getUniqueId().getId().equals(id))
.map(ViewData::getManagerId).findFirst().orElse("");
String empName = list.stream()
.filter(obj -> obj.getUniqueId().getId().equals(id))
.map(ViewData::getName).findFirst().orElse("");
}
【问题讨论】:
-
你可以添加样本输入和相应的预期输出吗?很难理解你的描述。
-
@Eran 添加了一个示例 i/p -> o/p。现在这段代码只返回每个员工的第一个 teamId。包括经理 ID 是可选的。但是过滤器和地图组合格式是否正确?我对此有疑问。基于一列进行过滤并将不同的列放入数组中。
-
输出的类型应该是什么?
-
@Eran 需要它为
String[] -
如何在单个字符串数组中存储每个员工 ID 的团队 ID 列表?听起来您需要
Map<String,List<String>>或Map<String,String[]>。
标签: java filter java-8 spring-data-jpa java-stream