fail-fast实现机制

Arraylist,HashMap,HashSet等容器持有的的fail-fast迭代器,具体实现原理和modcount域有关.

 Lets looks at following code 

01 public class FailFastIteratorTest {
02 
03   public static void main(String[] args) {
04     
05     final List<String> list = new ArrayList<String>();
06     list.add("a");
07     list.add("b");
08     list.add("c");
09     
10     Iterator<String> it = list.iterator();
11     
12     Thread t = new Thread() {
13 
14       public void run() {
15         list.add("d");
16         list.add("e");
17         list.add("f");
18       }
19     };
20     t.start();
21     
22     // Make sure, thread gets kicked off
23     try {
24       Thread.sleep(1000);
25     } catch (InterruptedException e) {
26     }
27     
28     while(it.hasNext()){
29       System.out.println(it.next());
30     }
31   }
32 }

What will happen when above program is run ? Hope you have guessed it right, you will get java.util.ConcurrentModificationException thrown at line it.next(). Because its not allowed for a thread to modify the collection, while another is iterating over it. Ok, lets make it single threaded and modify code (lines 06 to 30) as below: 

理解:当一个线程进行迭代遍历的时候,另一个线程对容器进行修改,会抛出CME异常.

1 list.add("a");
2 list.add("b");
3 list.add("c");
4 
5 Iterator<String> it = list.iterator();
6 list.add("d");
7 while(it.hasNext()){
8   System.out.println(it.next());
9 }

Huh!.. again you will get throw ConcurrentModificationException thrown at line it.next(). After the creation of Iterator, the container cannot be modified at any time by any method other than the Iterator's own remove or add methods. Iterators that do this are known as fail-fast iterators, as they fail quickly and cleanly, rather that risking arbitrary, non-deterministic behavior at an undetermined time in the future. Ok Now lets dig little deep and ascertain how fail-fast iterators are implemented. Java uses modCount variable to track number of modifications made. Here goes the javadoc comments for declaraion of modCount variable in AbstractList class. 

理解:当一个迭代器创建好之后就不能再用容器的remove或是add函数对容器进行修改,只能用迭代器的remove或add函数对容器进行修改,否则会抛出CME异常.接下来我们看看fail-fast的实现机制:java是通过modCount变量来跟踪容器的修改次数.

01 /**
02 * The number of times this list has been structurally modified.
03 * Structural modifications are those that change the size of the
04 * list, or otherwise perturb it in such a fashion that iterations in
05 * progress may yield incorrect results.
06 *
07 * This field is used by the iterator and list iterator implementation
08 * returned by the iterator and listIterator methods.
09 * If the value of this field changes unexpectedly, the iterator (or list
10 * iterator) will throw a ConcurrentModificationException in
11 * response to the next, remove, previous, set or add operations.  
12 * This provides fail-fast behavior, rather than non-deterministic behavior in
13 * the face of concurrent modification during iteration.
14 *
15 * Use of this field by subclasses is optional. If a subclass
16 * wishes to provide fail-fast iterators (and list iterators), then it
17 * merely has to increment this field in its add(int, Object) and
18 * remove(int) methods (and any other methods that it overrides
19 * that result in structural modifications to the list).  A single call to
20 * add(int, Object) or remove(int) must add no more than
21 * one to this field, or the iterators (and list iterators) will throw
22 * bogus ConcurrentModificationExceptions.  If an implementation
23 * does not wish to provide fail-fast iterators, this field may be
24 * ignored.
25 */
26 protected transient int modCount = 0;
27 
28 Now lets look at implementation iterator class returned by list.
29 
30 private class Itr implements Iterator<E> {
31   int expectedModCount = modCount;
32 
33   public boolean hasNext() {
34       // implementation omitted            
35   }
36 
37   public E next() {
38             checkForComodification();
39             // implementation omitted     
40       
41   }
42 
43   private void checkForComodification() {
44       if (modCount != expectedModCount)
45     throw new ConcurrentModificationException();
46   }
47  }

As it is clear, expectedModCount is initialized to modCount at creation of Iterator and any method that modify the list would increament modCount. Every call to next() method, checks expectedModCount and throws ConcurrentModificationException if it does not match with modCount. 

理解:fail-fast的实现机制:在迭代器创建的时候将exceptedModCount域初始化为modCount的值,任何对容器的修改都会改变modCount的值.每当调用next函数的时候,检查expectedModCount域和当前的modCount域是否相等,不相等的话则抛出CME异常.

转载于:https://www.cnblogs.com/Guoyutian/p/5185456.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值