Stream.close()是终端操作吗



StreamBaseStream中的每个方法都整齐地指定操作是中间还是(短路)终端。

例外的是close()方法,它只声明调用关闭处理程序。

我假设close()是一个终端操作,并且调用其他方法将导致IllegalStateException。然而,就目前情况来看,这似乎取决于执行情况。

Javadoc中的这一遗漏是疏忽还是故意的,我是不是遗漏了什么?

Stream.close()既不是中间操作,也不是终端操作。它实际上根本不是一个操作(在Stream API的意义上)。回想一下,在调用一个终端操作之后,不允许在同一个流上调用另一个操作。

然而,在终端操作之后,在Stream上调用close()不仅是允许的,而且是预期的使用,因此它不是那种流操作。关闭流的操作与禁止对流进行后续操作的终端操作具有相同的属性(以防由于已开始的终端操作而尚未禁止后续操作),这一点无可否认有点不明确。

但另一方面,这是close操作的正常行为,即使资源或对象不可用于后续操作,因此这也适用于Streams也不应令人惊讶。

在实践中,众所周知的错误消息不言自明,因为它将"已对进行操作"或"closed"命名为拒绝后续操作的两个相同原因。

我认为Stream.close()可以被视为终端操作流管道中的一种操作,它将流作为输入并产生结果或副作用。在执行终端操作之后,流管道被认为已被消耗,并且不能再使用

现在,如果您检查close()操作的实现,则如下所示:

public void close() {
    linkedOrConsumed = true; // it sets the flag consumed as true

现在,如果你试图访问流,比如说使用映射操作,你会得到一个IllegalStateException,因为在ReferencePipelines的构建过程中有检查。

    if (previousStage.linkedOrConsumed)
        throw new IllegalStateException(MSG_STREAM_LINKED);

尝试使用以下代码:

    Stream<String> stream = Arrays.stream(myStringNumbers); 
    stream.close();
    List<Integer> list1 = stream.map(Integer::parseInt).collect(toList());

上面的代码将抛出IllegalStateException

最新更新