为了账号安全,请及时绑定邮箱和手机立即绑定

如何通过多个属性找到重复的对象并将它们合并?

如何通过多个属性找到重复的对象并将它们合并?

达令说 2023-11-01 21:48:31
我正在编写一个验证函数,用于 MongoDb 中集合之间的数据标准化我有一个对象:如下所示:class ReleaseTime{  private Date startDate;  private Date endDate;  private List<String> regions;}我必须收集具有相同startDate和相同的所有 ReleaseTime 对象,endDate然后将区域列表合并在一起我已经尝试过下面的代码,但它只是按开始日期分组expectedAvailabilities = ungrouppedReleaseTime.stream()            .collect(Collectors.toMap(ReleaseTime::getStartDate,                    Function.identity(),                    (ReleaseTime tb1, ReleaseTime tb2) ->                    {                        tb1.getRegions().addAll(tb2.getRegions());                        tb2.getRegions().clear();                        return tb1;                    })            ).values();感谢您的帮助!
查看完整描述

2 回答

?
跃然一笑

TA贡献1826条经验 获得超6个赞

这是在不使用流的情况下执行您想要的操作的另一种方法:


Map<List<Date>, List<String>> map = new LinkedHashMap<>();

ungrouppedAvailabilites.forEach(a ->

    map.computeIfAbsent(Arrays.asList(a.getStartDate(), a.getEndDate()), // or List.of

                        k -> new ArrayList<>())

       .addAll(a.getRegions()));

这用于按开始日期和结束日期对对象Map.computeIfAbsent区域进行分组ReleaseTime。


如果分组ReleaseTime对象之间存在重复区域并且您不希望重复,则可以使用 aSet而不是 a List:


Map<List<Date>, Set<String>> map = new LinkedHashMap<>();

ungrouppedAvailabilites.forEach(a ->

    map.computeIfAbsent(Arrays.asList(a.getStartDate(), a.getEndDate()), // or List.of

                        k -> new LinkedHashSet<>())

       .addAll(a.getRegions()));

请注意,我使用LinkedHashMap和LinkedHashSet来保持元素的插入顺序。


编辑:


如果您需要ReleaseTime对象而不仅仅是其区域,则可以通过一个额外步骤来实现:


Map<List<Date>, ReleaseTime> result = new LinkedHashMap<>();

map.forEach((k, v) -> 

    result.put(k, new ReleaseTime(k.get(0), k.get(1), new ArrayList<>(v))));

这假设有一个ReleaseTime接收所有属性的构造函数:


public ReleaseTime(Date startDate, Date endDate, List<String> regions) {

    this.startDate = startDate;

    this.endDate = endDate;

    this.regions = regions;

}


查看完整回答
反对 回复 2023-11-01
?
浮云间

TA贡献1829条经验 获得超4个赞

您可以将分组用作:


// Collection<ReleaseTime> ungrouppedAvailabilites...

Collection<ReleaseTime> mergedRegionsCollection = ungrouppedAvailabilites.stream()

        .collect(Collectors.toMap(t -> Arrays.asList(t.getStartDate(), t.getEndDate()),

                Function.identity(), ReleaseTime::mergeRegions))

        .values();

其中mergeRegions实现为:


ReleaseTime mergeRegions(ReleaseTime that) {

    List<String> mergedRegions = this.getRegions();

    mergedRegions.addAll(that.getRegions());

    return new ReleaseTime(this.startDate, this.endDate, mergedRegions);

}

注意:为了避免改变现有对象,您可以使用以下实现:


ReleaseTime mergeRegions(ReleaseTime that) {

    return new ReleaseTime(this.startDate, this.endDate,

            Stream.concat(this.getRegions().stream(), that.getRegions().stream())

                    .collect(Collectors.toList()));

}


查看完整回答
反对 回复 2023-11-01
  • 2 回答
  • 0 关注
  • 117 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信