Что приводит к ConcurrentModificationException - PullRequest
0 голосов
/ 18 мая 2018

Я читал об исключении ConcurrentModificationException.Я нашел этот кусок кода для итератора. Кто-нибудь может объяснить, что на самом деле приводит к этому исключению. Я просто хочу получить некоторое оправдание для логики, написанной ниже.

public boolean hasNext() {
    return cursor != size;
}

@SuppressWarnings("unchecked")
public E next() {
    checkForComodification();
    int i = cursor;
    if (i >= size)
        throw new NoSuchElementException();
    Object[] elementData = ArrayList.this.elementData;
    if (i >= elementData.length)
        throw new ConcurrentModificationException();
    cursor = i + 1;
    return (E) elementData[lastRet = i];
}

public void remove() {
    if (lastRet < 0)
        throw new IllegalStateException();
    checkForComodification();

    try {
        ArrayList.this.remove(lastRet);
        cursor = lastRet;
        lastRet = -1;
        expectedModCount = modCount;
    } catch (IndexOutOfBoundsException ex) {
        throw new ConcurrentModificationException();
    }
}

final void checkForComodification() {
    if (modCount != expectedModCount)
        throw new ConcurrentModificationException();
    }
}

1 Ответ

0 голосов
/ 18 мая 2018

Ваше базовое число элементов меняет размер, пока вы перебираете их, поэтому возникает исключение.

Обратите внимание, что попытка здесь не в том, чтобы оправиться от невозможной ситуации, а в том, чтобы "потерпеть неудачу"как можно раньше и чисто.Вероятно, было бы довольно легко не выбросить исключение и заставить что-то работать, но поведение не определено.Это делает все возможное, чтобы убедиться, что в вашем итераторе нет ошибки кодирования, а не просто восстанавливаться из невозможного угла кода.

// This line is getting the underlying array out from "this" ArrayList   
Object[] elementData = ArrayList.this.elementData; 

// I is the current value of your cursor.  Every time you call "next"
// this cursor is being incremented to get the next value
// This statement is asking if your current cursor extends beyond the
// end of the array, if it does then "Something" happened to make the array
// smaller while we weren't looking...
if (i >= elementData.length) 
    // To indicate that the elementData array has changed size outside of
    // our current iterator, throw an exception to the user.
    throw new ConcurrentModificationException();

Итак, чтобы это произошло, вы должны создатьитератор, затем уменьшите размер списка массивов, затем вызовите «Далее».Это должно дать вам CME

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...