简体   繁体   中英

Updating a List of Object from another list of object using java stream

I have a list of Object A

A{
name
age
dob
}

and list of Object B

B{
name
dob
}

.

I always get the List of A with A.dob as null. and List of B with B.dob having value. I need to loop thru List of A and List of B find the common objects using the name field in each A and B object and update A.dob using B.dob

Can this be done using streams?

I'd suggest modifying the list of A objects in a forEach loop:

// define: List<A> aList =

// define: List<B> bList =


aList.forEach(aListElement -> {
            // find the first B object with matching name:
            Optional<B> matchingBElem = bList.stream()
                    .filter(bElem -> Objects.equals(aListElement.getName(), bElem.getName()))
                    .findFirst();

            // and use it to set the dob value in this A list element:
            if (matchingBElem.isPresent()) {
                aListElement.setDob(matchingBElem.get().getDob());
            }

        }
);

You should not use Stream APIs to change the state of an Object.

If you still want to modify it then, You can iterate each element from the list of A , filter if dob is null, find dob against the respective name in the list of B .

List<A> aList = new ArrayList<>();
List<B> bList = new ArrayList<>();

aList.stream()
        .filter( a  -> a.dob == null)
        .forEach( a -> {
            Predicate<B> nameFilter = b -> b.name.equals(a.name);
            a.dob = findDob(nameFilter, bList);
        });

static String findDob(Predicate<B> nameFilter, List<B> bList) {
    B b = bList.stream()
            .filter(nameFilter)
            .findFirst()
            .orElse(new B());

    return b.dob;
}

Alternate efficient solution: Considering you have a unique name for each object B, you can prepare lookup and find age using that map, this way you do not need to iterate bList for every iteration of aList

List<A> aList = new ArrayList<>();
List<B> bList = new ArrayList<>();

Map<String, String> nameDobLookup = bList.stream()
                        .collect(Collectors.toMap(b -> b.name, b -> b.dob));

aList.stream()
        .filter(a -> a.dob == null)
        .forEach(a -> a.dob = nameDobLookup.get(a.name));

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM