通过迭代改变集合

时间:2012-02-20 01:05:25

标签: java exception collections iteration

修改一组迭代有时会创建一个异常,有时则不会,为什么?

并发修改异常

       Set<Integer> j = new HashSet<Integer>();
       j.add(23);
       j.add(45);
       j.add(64);
       int c=0;
       for(Integer k: j)
       {
         if(c++==0)
         {
             j.remove(45);
         }
       }
      System.out.println(j); // concurrent modification exception

     <hr>

 //works without exception
     Set<Integer> j = new HashSet<Integer>();
       j.add(23);
       j.add(45);
       j.add(64);
       int c=0;
    for(Integer k: j)
    {
       if(k==45)
       {
           j.remove(45);
       }
    }
    System.out.println(j);//works without exception

1 个答案:

答案 0 :(得分:4)

来自JavaDocs for HashSet

  

此类的迭代器方法返回的迭代器是快速失败的:如果在创建迭代器之后的任何时间修改了集合,除了通过迭代器自己的remove方法之外,Iterator抛出ConcurrentModificationException。因此,面对并发修改,迭代器会快速而干净地失败,而不是在未来不确定的时间冒着任意的,非确定性行为的风险。

     

请注意,无法保证迭代器的快速失败行为,因为一般来说,在存在不同步的并发修改时,不可能做出任何硬性保证。失败快速迭代器会尽最大努力抛出ConcurrentModificationException。因此,编写依赖于此异常的程序以确保其正确性是错误的:迭代器的快速失败行为应仅用于检测错误。

(突出显示是我的。)