【问题标题】:Iterator invalidation rules in JavaJava中的迭代器失效规则
【发布时间】:2021-04-11 11:55:11
【问题描述】:

我正在研究 Java 中的迭代器失效规则,但我找不到像 this 这样适用于 C++ 的正确信息。我为 java 找到的所有东西都更通用,比如 this one。有我可以遵循的文档吗?

【问题讨论】:

    标签: java collections iterator


    【解决方案1】:

    Java“集合框架概述”documentation

    通用实现支持集合接口中的所有可选操作,并且对它们可能包含的元素没有限制。它们是不同步的,但 Collections 类包含称为同步包装器的静态工厂,可用于将同步添加到许多不同步的集合中。所有的新实现都有快速失败的迭代器,它可以检测无效的并发修改,并快速而干净地失败(而不是行为不规律)。

    Java 具有并发线程安全的集合实现。它们是java.util.concurrent 包的一部分,文档说

    大多数并发集合实现(包括大多数队列) 也不同于通常的 java.util 约定,因为它们的 迭代器和拆分器提供弱一致而不是 快速失败遍历:

    • 它们可能与其他操作同时进行
    • 他们永远不会抛出 ConcurrentModificationException
    • 保证它们会遍历元素,因为它们在构造时就存在一次,并且可能(但不保证)反映 施工后的任何修改。

    例如ConcurrentHashMap

    类似地,迭代器、拆分器和枚举返回的元素反映了在迭代器/枚举创建时或之后的某个时刻哈希表的状态。它们不会抛出 ConcurrentModificationException。但是,迭代器被设计为一次只能由一个线程使用。请记住,包括 size、isEmpty 和 containsValue 在内的聚合状态方法的结果通常仅在地图未在其他线程中进行并发更新时才有用。否则,这些方法的结果反映的瞬态状态可能足以用于监控或估计目的,但不适用于程序控制。

    所以简短的回答是:如果您想迭代集合,而它可能会被另一个线程更改,只需使用并发实现集合。这个 java 迭代器在“C++ 含义”中永远不会失效

    或者只是使用线程不安全的集合并捕获ConcurrentModificationException 来修复集合修改问题。在这种情况下,java迭代器在“C++含义”中也永远不会失效。

    【讨论】:

      猜你喜欢
      • 2011-09-20
      • 2017-10-05
      • 2016-10-26
      • 2023-01-13
      • 2017-04-11
      • 1970-01-01
      相关资源
      最近更新 更多