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

在一个流中过滤和设置()

在一个流中过滤和设置()

叮当猫咪 2022-06-08 17:03:44
所以我有一些我正在玩的示例代码来尝试找出下面的逻辑。它只是一个大的 main 方法和两个 POJO,但它会运行。我正在调试以获取终止点的值。public class Main {    public static void main(String[] args) {        obj1 obj1 = new obj1();        obj1 obj12 = new obj1();        obj2 obj2 = new obj2();        obj2 obj22 = new obj2();        obj1.id = 123L;        obj1.carId = 1234L;        obj12.id = 123L;        obj12.carId = 1234L;        obj2.carId = 1234L;        obj22.carId = 12345L;        ArrayList<obj1> obj1Arr = new ArrayList<>();        ArrayList<obj2> obj2Arr = new ArrayList<>();        obj1Arr.add(obj1);        obj1Arr.add(obj12);        obj2Arr.add(obj2);        obj2Arr.add(obj22);        List<obj2> newCarList= obj2Arr.stream()                .filter(anObjOf2 -> obj1Arr                        .stream()                        .anyMatch(carReg -> carReg.getCarId().equals(anObjOf2.getCarId())))                .collect(Collectors.toList());    }}POJO1:public class obj1 {    Long id = null;    Long carId = null;    public Long getId() {        return id;    }    public void setId(Long id) {        this.id = id;    }    public Long getCarId() {        return carId;    }    public void setCarId(Long carId) {        this.carId = carId;    }}POJO2:public class obj2 {    Long id = null;    Long carId = null;    public Long getId() {        return id;    }    public void setId(Long id) {        this.id = id;    }    public Long getCarId() {        return carId;    }    public void setCarId(Long carId) {        this.carId = carId;    }}如您所见,我正在流式传输并过滤掉任何obj与carId. 我的下一个目标是然后set id(不是 carId)在匹配的对象上。基本上,如果obj1.carId == obj2.carIdTHEN set obj1.id = obj2.id。我的问题是我不知道如何在同一个流中做到这一点。可能吗?我不禁认为此时需要一个迭代器?
查看完整描述

3 回答

?
交互式爱情

TA贡献1712条经验 获得超3个赞

不要在一个流中执行这两个操作。这是一种非常糟糕的风格。


先收集数据。然后变异元素。就像是:


Map<obj2, Optional<obj1>> map = 

    obj2Arr.stream()

           .collect(toMap(identity(), o2 -> obj1Arr.stream()

                                                  .filter(o1 -> o1.getCarId().equals(o2.getCarId()))

                                                  .findAny()));


map.forEach((o1, optO2) -> optO2.ifPresent(o2 -> o1.setId(o2.id)));

否则,您可以只使用嵌套的 for-each 循环。


查看完整回答
反对 回复 2022-06-08
?
翻过高山走不出你

TA贡献1875条经验 获得超3个赞

我建议首先为第一个列表中的每个元素创建一个映射Map(我已经修改了你的类以使其更具可读性并删除了重复的 ID,我认为这是一个错误):carIdid


@Data @AllArgsConstructor

class Car {

    Long id = null;

    Long carId = null;

}

List<Car> obj1Arr = Arrays.asList(new Car(1L, 123L), new Car(2L, 1234L));

List<Car> obj2Arr = Arrays.asList(new Car(0L, 1234L), new Car(0L, 12345L));


Map<Long, Long> carIdToId = obj1Arr.stream()

        .collect(Collectors.toMap(Car::getCarId, Car::getId));

// [Car(id=2, carId=1234), Car(id=0, carId=12345)]

然后,您可以使用它Map来过滤具有相同的汽车,carID而无需与其他汽车进行比较。然后,forEach只需在原始列表中设置 Id。


obj2Arr.stream()

        .filter(anObjOf2 -> carIdToId.containsKey(anObjOf2.getCarId()))

        .forEach(anObjOf2 -> anObjOf2.setId(carIdToId.get(anObjOf2.getCarId())));

System.out.println(obj2Arr);

// [Car(id=2, carId=1234), Car(id=0, carId=12345)]

如果您只想要相等的项目,您可以在然后carId设置ID 。不过,这仍会修改原始实例:peekcollect


obj2Arr = obj2Arr.stream()

        .filter(anObjOf2 -> carIdToId.containsKey(anObjOf2.getCarId()))

        .peek(anObjOf2 -> anObjOf2.setId(carIdToId.get(anObjOf2.getCarId())))

        .collect(Collectors.toList());

System.out.println(obj2Arr);

// [Car(id=2, carId=1234)]

或者创建一个全新实例的列表:


obj2Arr = obj2Arr.stream()

        .map(Car::getCarId)

        .filter(carIdToId::containsKey)

        .map(carId -> new Car(carIdToId.get(carId), carId))

        .collect(Collectors.toList());

System.out.println(obj2Arr);

// [Car(id=2, carId=1234)]


查看完整回答
反对 回复 2022-06-08
?
慕勒3428872

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

你可以在谓词中做到这一点anyMatch


List<obj2> newCarList= obj2Arr.stream()

            .filter(anObjOf2 -> obj1Arr

                    .stream()

                    .anyMatch(carReg ->  {

            if(carReg.getCarId().equals(anObjOf2.getCarId()))) {

                 carReg.setId(anObjOf2.getId());

                  return true;

               }

           return false;

     }).collect(Collectors.toList());

第二种方法


先过滤


List<obj2> newCarList= obj2Arr.stream()

            .filter(anObjOf2 -> obj1Arr

                    .stream()

                    .anyMatch(carReg -> carReg.getCarId().equals(anObjOf2.getCarId())))

            .collect(Collectors.toList());

现在设置id


newCarList.forEach(obj->{

           obj1Arr.forEach(o-> {

            if(o.getCarId().equals(obj.getCarId()) {

                  o.setId(obj.getId());

                }

           };

    });


查看完整回答
反对 回复 2022-06-08
  • 3 回答
  • 0 关注
  • 122 浏览

添加回答

举报

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