I have an interface and its parameter can be null.
int count(@Nullable F filter);
To avoid null parameters and null checks common advise is to use the method overloading:
int count();
int count(@NonNull F filter);
In some cases I don't like this approach, because it forces clients to make this kind of job:
F f = getFilter()
f != null ? count(f) : count()
It much more convenient for client to use:
count(getFilter())
Optionals, at the first glance, can solve this problem but "Optional" should not be used for parameters https://rules.sonarsource.com/java/RSPEC-3553
So my question is: can I use Supplier instead?
//service code:
int count(Supplier<F> filter) {
Optional.ofNullable(filter.get()).map(f->count(f)).orElseGet(() -> count());
};
//client code:
count(() -> getFilter())
Or even
int count(Supplier<Optional<F>> filter)
Idea doesn't show any warnings.
I personally like my code after that, but isn't it cheating? Why it's better then Optional?
EDIT: Thanks for comments. I agree, in my case Supplier is just a sophisticated @Nullable approach.
I will return to:
int count();
int count(@NonNull F filter);
/////
getFilter().map(f->count(f)).orElseGet(() -> count());
CodePudding user response:
If you don't want the client-code to dial with null
, you can change the method getFilter()
to return Optional<F>
.
In this case, the code in the client would look like that:
int count = getFilter().map(MyClass::count).orElse(MyClass.count());
With this approach, your method count(F)
doesn't require any extra logic.
If it feels like too complicated, then can implement count(F)
in such a way that it would delegate to count()
in case if provided argument is null
.
Both your attempt with Supplier<F>
and Supplier<Optional<F>>
are artificial and seem to be driven by intention to circumvent Sonar, rather than by the real use cases.