DEV Community

Andrey Sviridov
Andrey Sviridov

Posted on

A way initialization in streams and collections.

Let's consider, we have to validate fields in the object according to some logic. I provide an example of this class.

@Data
public class Example {
    private String a;
    private String b;
    private String c;
    private String d;
}
Enter fullscreen mode Exit fullscreen mode

All fields are nullable. If field "a" is present then field "b" has to be present too. If field "c" is blank then field "d" has to be blank too.
My first variant is

public class Validator {

    public void validate(Example example) {
        List.of(example.getA(), example.getB(), example.getC(), example.getD())
                .forEach(this::validateSomeLogic);
    }

    private void validateSomeLogic(String example) {
        ...
    }
}
Enter fullscreen mode Exit fullscreen mode

Assume, once we receive null for a field, in this case we get NPE. The straightforward solution to prevent the error will be the null check definition before adding a value to the list.
Let's see what happens.

public class Validator {

    public void validate(Example example) {
        List<String> list = new ArrayList<>();
        if (exapmle.getA() != null) list.add(example.getA());
        if (exapmle.getB() != null) list.add(example.getB());
        if (exapmle.getC() != null) list.add(example.getC());
        if (exapmle.getD() != null) list.add(example.getD());
        list.forEach(this::validateSomeLogic);
    }

    private void validateSomeLogic(String example) {
        ...
    }
}
Enter fullscreen mode Exit fullscreen mode

It works but it looks a little bit clumsy. Do we have a way to do lazy initialization?
One of the differences between collections and streams is that streams support lazy initialization.

public class Validator {

    public void validate(Example example) {
        Stream.of(example.getA(), example.getB(), example.getC(), example.getD())
                .filter(Objects::nonNull)
                .forEach(this::validateSomeLogic);
    }

    private void validateSomeLogic(String example) {
        ...
    }
}
Enter fullscreen mode Exit fullscreen mode

It looks much better! I think this example is good to demonstrate the differences between types of initializations in collections and streams.

Discussion (0)