Collection – Iterator.remove()vs Collection.remove()
按照Sun,
“Iterator.remove是在迭代期间修改集合的唯一安全方法;如果在迭代进行过程中以任何其他方式修改基础集合,则行为未指定。”
我有两个问题:
- 是什么让这个操作“Iterator.remove()”比其他操作稳定?
- 如果它在大多数用例中没用,它们为什么提供“Collection.remove()”方法呢?
如果您正在迭代集合并使用:
Collection.remove()
您可以获得运行时错误(特别是ConcurrentModifcationException),因为您正在更改先前使用的对象的状态,以构造完成循环所需的显式调用序列。
如果您使用:
Iterator.remove()
告诉运行时您想要更改底层集合并重新评估完成循环所需的显式调用系列。
首先, Collection.remove()
非常有用。 它适用于很多用例,可能比Iterator.remove()
。
但是,后者解决了一个特定问题:它允许您在迭代时修改集合。
Iterator.remove()
解决的问题如下所示:
List l = new ArrayList (Arrays.asList(1, 2, 3, 4)); for (int el : l) { if (el < 3) { l.remove(el); } }
此代码无效,因为l.remove()
在迭代过程中调用l
。
以下是编写它的正确方法:
Iterator it = l.iterator(); while (it.hasNext()) { int el = it.next(); if (el < 3) { it.remove(); } }
正如您引用的文档明确指出的那样,
Iterator.remove是在迭代期间修改集合的唯一安全方法
(重点补充)
使用am迭代器时,除了通过调用Iterator.remove()
之外,您无法修改集合。
如果您没有迭代集合,则可以使用Collection.remove()
。
是什么让这个操作“Iterator.remove()”比其他操作稳定?
这意味着迭代器知道您删除了元素,因此它不会产生ConcurrentModifcationException。
如果它在大多数用例中没用,它们为什么提供“Collection.remove()”方法呢?
通常你会使用Map.remove()或Collection.remove(),因为这比迭代每个对象更有效。 如果你经常迭代删除我怀疑你应该使用不同的集合。
-
只是一个设计选择。 可以指定不同的行为(即迭代器必须跳过由Collection.remove()删除的值),但这会使集合框架的实现变得更加复杂。 所以选择不加以指定。
-
这非常有用。 如果您知道要删除的对象,为什么要迭代?
据我所知,Collection.remove(int index)也将返回被删除的对象。 Iterative.remove()不会。