Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/357.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 我必须在流读取的列表上进行同步吗?_Java_Java 8_Java Stream - Fatal编程技术网

Java 我必须在流读取的列表上进行同步吗?

Java 我必须在流读取的列表上进行同步吗?,java,java-8,java-stream,Java,Java 8,Java Stream,如果我有一个线程敏感列表,我在迭代时通常会这样做: List list = Collections.synchronizedList(new ArrayList()); ... synchronized(list) { Iterator i = list.iterator(); // Must be in synchronized block while (i.hasNext()) foo(i.next()); } 我想知道我是否使用list.st

如果我有一个线程敏感列表,我在迭代时通常会这样做:

    List list = Collections.synchronizedList(new ArrayList());
...
synchronized(list) {
    Iterator i = list.iterator(); // Must be in synchronized block
    while (i.hasNext())
        foo(i.next());   
}
我想知道我是否使用list.stream(),然后在流上执行一些操作,如过滤器等,如果我还必须将列表放入同步块中,或者流是否复制了列表


感谢流操作在内部使用
spliterator()
方法

以下是
ArrayList
中的
spliterator()
方法:

    public Spliterator<E> spliterator() {
        checkForComodification();
        return new ArrayListSpliterator<E>(ArrayList.this, offset,
                                           offset + this.size, this.modCount);
    }
这与迭代器()中的注释类似:

流可以看作是原始数据的“视图”。这意味着:避免复制是他们天性的一部分


只有排序等操作需要创建输入的副本。因此:当您的输入可以被另一个线程更改时,您需要对此进行保护

是的,使用流时必须同步对列表的访问,就像不使用流时一样。同步应由用户负责

流本身并不保证创建原始序列的任何副本。它可以在某些中间计算(例如,
排序
)期间复制,但您不应依赖于此。对于流的每一次使用,这样做都是对资源的浪费

例如,如果用户希望流在副本上运行,他们必须手动创建副本或使用
CopyOnWriteArrayList
而不是
ArrayList

此外,请记住这一点。在执行终端操作(例如,
collect
forEach
)之前,不会访问底层序列

    public Spliterator<E> spliterator() {
        return c.spliterator(); // Must be manually synched by user!
    }
    public Iterator<E> iterator() {
        return c.iterator(); // Must be manually synched by user!
    }
    public Stream<E> stream() {
        return c.stream(); // Must be manually synched by user!
    }