Gopal S Akshintala
Gopal S Akshintala

Reputation: 1973

Why no public constructor for Optional in java?

Why does Optional have methods like of() and ofNullable() instead of a public constructor?

Upvotes: 32

Views: 4190

Answers (4)

davidxxx
davidxxx

Reputation: 131486

Because factory methods should be favored over public constructors when the possible instantiation cases are known.
It makes the API easier to use for client classes.
Besides factory methods allow to decide whether an instance should be created at each invocation.
In the case of Optional.empty() it makes sense to cache the value as that is immutable.

Upvotes: 9

Stefan Repcek
Stefan Repcek

Reputation: 2603

From Joshua Bloch effective Java, Chapter 2. Creating and Destroying Objects, 1 Item:

Consider static factory methods instead of constructors

Why?

One advantage of static factory methods is that, unlike constructors, they have names.

With static factory methods we can specify some instantiation behavior in the method definition. This makes the API easier to use and we prevent clients from calling wrong constructors.

For instance here: In Optional.ofNullable -> we allow null value be passed to instantiate the Optional, in Optional.of null value is not allowed and throw exception. We could not use the constructor here.

private Optional(T value) {
    this.value = Objects.requireNonNull(value); //this throws NullPointerException
}
public static <T> Optional<T> of(T value) {
        return new Optional<>(value);
}
public static <T> Optional<T> ofNullable(T value) {
        return value == null ? empty() : of(value);
} 

Another advantage (already mentioned):

A second advantage of static factory methods is that, unlike constructors, they are not required to create a new object each time they’re invoked.

In Optional, the empty value is instantiated just once, and then stored in the static field, this value is reused always when the program needs an empty value.

private static final Optional<?> EMPTY = new Optional<>(); //instantiate value when program starts

public static<T> Optional<T> empty() {
    @SuppressWarnings("unchecked")
    Optional<T> t = (Optional<T>) EMPTY; //return stored value when requested
    return t;
}

Upvotes: 39

Minn
Minn

Reputation: 6134

The reason is actually quite simple: an empty optional is a static constant to be more memory efficient. If a constructor were used, it would have to create a new instance every time for a common case.

public static<T> Optional<T> empty() {
    @SuppressWarnings("unchecked")
    Optional<T> t = (Optional<T>) EMPTY;
    return t;
}

public static <T> Optional<T> ofNullable(T value) {
    return value == null ? empty() : of(value);
}

Upvotes: 21

Ori Marko
Ori Marko

Reputation: 58822

Optional is a Value-based Class without any constructors

do not have accessible constructors, but are instead instantiated through factory methods which make no committment as to the identity of returned instances

Upvotes: 10

Related Questions