Java中空Optional的类型是什么?

6

事情是这样的,我在查看Java的Optional类,并注意到在public static<T> Optional<T> empty()文档中有以下内容:

@param <T> The type of the non-existent value*.

在查看整个类并搜索这里和其他一些页面之后,我遇到了这个问题,我无法回答:

  1. 一个空的Optional可以有特定的类型吗? 1.1 如果可以,如何设置它? 1.2 是否有任何方法检查其类型?

2
泛型类型参数在运行时不存在。因此,空的 Optional 对象的类型只是 Optional。当您需要一个空的 Optional<T> 时,编译器可以假定上下文所需的任何泛型类型 T;这不会导致问题,因为其中没有对象是错误类型。 - khelwood
类型推断,从你想要存储/分配的位置开始。 - Eklavya
@Eklavya 但是如果我不存储它呢?不存在值的整个“_type_”使我感到困惑。 - Ignacio Rodríguez Suárez
考虑它像(T) null一样模糊(尽管不是null)。empty()是一个函数而不是类常量的原因是你可以有一个带类型的Optional<T>值。 - Joop Eggen
我认为你首先想要研究Java泛型。Optional中没有任何与其他泛型类不同的地方... - GhostCat
1
这与 List<String> list1 = Collections.emptyList(); List<Integer> list2 = Collections.emptyList(); 没有任何不同,列表的类型仅由它们的引用变量决定。因此,或许令人惊讶的是,list1 == (Object)list2 将为 true。对于 Function<String,String> f1 = Function.identity(); Function<Integer,Integer> f2 = Function.identity(); 也是一样的。 - Holger
3个回答

10

它是您指定的任何类型:

// Empty Optional with value type String
Optional<String> opt = Optional.empty();

这是来自于 OpenJDK 11 的该方法的源代码

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

EMPTY 是一个静态实例(源代码链接如上):

    /**
     * Common instance for {@code empty()}.
     */
    private static final Optional<?> EMPTY = new Optional<>();

6

Optional类是一个可能包含特定元素的容器。因此,它具有两个概念:

  • 它可能包含的类型
  • 它所包含的实际对象

它可能包含的类型是通过泛型指定的。泛型只存在于编译时期,并在运行时丢失。

回答您的问题:

  1. 当使用Optional时,通常定义它可能包含某种类型,如下所示:
Optional<String> optionalString;

此时我们知道optionalString可能会包含一个字符串。如果我们这样做:

Optional<String> optionalString = Optional.empty();

它实际上并不包含任何内容,但我们可以在任何需要Optional<String>的地方使用它。

  1. Optional类型会根据其使用进行推断。就像上面一样,您可以指定Optional.empty()Optional<String>。您也可以通过方法的返回值来指定其类型,如下所示:
public Optional<Integer> findNumber() {
    return Optional.empty();
}
  1. 由于类型在运行时不再存在,因此此时无法检查可选项包含的内容。在运行时,空的Optional没有类型。

你可以使用以下方式创建一个特定类型的空值:Optional.<String>empty(); - undefined

1
我知道已经有一篇博客文章的链接了,但我总是参考这个链接:Baeldung Java Optional 8 对于你的问题:
1. Optional可以包含任何对象类型(如果需要整数,则使用Integer)。 2. Optional.of(urObject),现在“类型”是Optional。 3. 您不能检查Optional的类型。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接