在 TreeSet 上使用迭代器
情况:我有一个自定义对象的 TreeSet,并且还使用了一个自定义比较器。我创建了一个迭代器来在此 TreeSet 上使用。
TreeSet<Custom> ts=new TreeSet<Custom>();
Iterator<Custom> itr=ts.iterator();
while(itr.hasNext()){
Custom c=itr.next();
//Code to add a new element to the TreeSet ts
}
问题:我想知道,如果我在 while 循环中向 TreeSet 添加一个新元素,那么该新元素是否会立即排序。换句话说,如果我在 while 循环中添加一个新元素,并且它小于我当前在 c 中保存的元素,那么在下一次迭代中我会在 c 中获得与上一次迭代相同的元素吗?(因为排序后,新添加的元素将占据当前元素之前的某个位置)。
SITUATION: I have a TreeSet of custom Objects and I have also used a custom Comparator. I have created an iterator to use on this TreeSet.
TreeSet<Custom> ts=new TreeSet<Custom>();
Iterator<Custom> itr=ts.iterator();
while(itr.hasNext()){
Custom c=itr.next();
//Code to add a new element to the TreeSet ts
}
QUESTION: Well I want to know that if I add a new element to the TreeSet within the while loop, then will that new element get sorted immediately. In other words, if I add a new element within the while loop and it is less than the one which I am currently holding in c, then in the next iteration will I be getting the same element in c as in the last iteration?(since after sorting, the newly added element will occupy a place somewhere before the current element).
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(7)
如果您在迭代期间添加元素,则下一次迭代器调用可能会抛出
ConcurrentModificationException
。请参阅 TreeSet 文档中的快速失败行为。要迭代和添加元素,您可以首先复制到另一个集合:
或者创建一个单独的集合,以便在迭代后与 ts 合并,正如 Colin 建议的那样。
If you add an element during your iteration, your next iterator call will likely throw a
ConcurrentModificationException
. See the fail-fast behavior in TreeSet docs.To iterate and add elements, you could copy first to another set:
or create a separate collection to be merged with
ts
after iteration, as Colin suggests.如果您在 while 循环内将元素添加到 TreeSet 中,您将得到一个 java.util.ConcurrentModificationException 。
###输出
You will get a java.util.ConcurrentModificationException if you add an element into the TreeSet inside while loop.
###Output
这将适用于所有集合,例如
List
、Map
、Set
因为当迭代器启动时,它可能会对其施加一些锁定。
如果您使用迭代器迭代列表,则会出现此异常。我认为否则这个循环将是无限的,因为您正在添加元素整个迭代。
考虑不使用迭代器:
这样就可以了。
This will come to all collections like
List
,Map
,Set
Because when iterator starts it may be putting some lock on it .
if you iterate list using iterator then this exception will come. I think otherwise this loop will be infinite as you are adding element whole iterating.
Consider without iterator:
this will be fine .
为了避免
ConcurrentModificationException
您可能需要查看我的UpdateableTreeSet
。我什至添加了一个新的 测试用例,展示如何在循环期间添加元素。更准确地说,您可以标记新元素以供以后延迟更新集合。这效果非常好。基本上你会做类似的事情,我想这正是你所需要的。 <代码>:-)
In order to avoid the
ConcurrentModificationException
you might want to check out myUpdateableTreeSet
. I have even added a new test case showing how to add elements during a loop. To be more exact, you mark new elements for a later, deferred update of the set. This works quite nicely. Basically you do something likeI guess this is quite exactly what you need.
:-)
防止行走时出现ConcurrentModificationException。
下面是我的版本,允许高频插入 TreeSet() 并允许同时对其进行迭代。当 TreeSet 迭代时,此类使用额外的队列来存储插入对象。
To prevent the ConcurrentModificationException while walking.
Below is my version to allow high frequency insertion into the TreeSet() and allow concurrently iterate on it. This class use a extra queue to store the inserting object when the TreeSet is being iterating.
虽然问题已经得到解答,但我认为最令人满意的答案在于 TreeSet 本身的 javadoc
While the question has already been answered, I think the most satisfactory answer lies in javadoc of TreeSet itself
为了避免在执行插入时必然发生的并发修改错误,您还可以创建 Set 的临时副本,改为迭代副本,然后修改原始副本。
To avoid the concurrent modification error that's bound to occur when you're doing the insertion, you could also create a temporary copy of the Set, iterate through the copy instead, and modify the original.