// java.util.ArrayList
protected transient int modCount = 0; // 내부적으로 가지고 있는 변수
...
public boolean add(E e) { // 추가 시
modCount++; // modCount 증가
add(e, elementData, size);
return true;
}
...
private void fastRemove(Object[] es, int i) { // 삭제 시 최종 호출되는 함수
modCount++; // modCount 증가
final int newSize;
if ((newSize = size - 1) > i)
System.arraycopy(es, i + 1, es, i, newSize - i);
es[size = newSize] = null;
}
next()가 호출될 때마다 modCounter가 변했는지 비교를 한다.
modCounter가 변했다면? ⇒ ConcurrentModificationException 발생 ⇒ 동작 중지
import java.util.ArrayList;
import java.util.Iterator;
public class FailSafeTest {
public static void main(String[] args) {
ArrayList<Integer> numbers = new ArrayList<>();
numbers.add(1);
numbers.add(2);
Iterator<Integer> iterator = numbers.iterator();
while (iterator.hasNext()) {
Integer number = iterator.next(); // ConcurrentModificationException 발생
numbers.add(50);
}
}
}
Iterator의 remove()를 사용해서 항목을 제거하면 ConcurrentModificationException이 발생하지 않는다.
expectedModCount
를 업데이트 한다.public class FailSafeTest {
public static void main(String[] args) {
ArrayList<Integer> numbers = new ArrayList<>();
numbers.add(10);
numbers.add(30);
numbers.add(40);
Iterator<Integer> iterator = numbers.iterator();
while (iterator.hasNext()) {
if (iterator.next() == 30) {
iterator.remove(); // ok!
}
}
for (Integer number : numbers) {
System.out.println("number = " + number); // 10, 40
}
}
}