Impossible IndexOutOfBound happening on ArrayList.get(). Any clue?
<p>I've got a very strange error, that would like to share with you.</p>

<p>I've the following code (simplified):</p>

<pre><code>public ArrayList&lt;String&gt; al = new ArrayList&lt;String&gt;();
public void doSomething() {
  int size = al.size();
  for(int i=0; i&lt;size; i++) {
    if (al.get(i) != null) {
      System.out.println(al.get(i));
      String sPath = al.get(i);
      File fFile = new File(sPath);
      fFile.delete(); // Simplified. It has some error checking
    }
  }
}
</code></pre>

<p>I have one error, saw in the production environment:</p>

<pre><code>java.lang.IndexOutOfBoundsException: Index: 1, Size: 0
    at java.util.ArrayList.RangeCheck(Unknown Source)
    at java.util.ArrayList.get(Unknown Source)
    at MYCLASS.soSomething(MICLASS.java:1944)
    [...]
</code></pre>

<p>Line 1944 is <code>if (al.get(i) != null) {</code>.</p>

<p>What! How can it raise IndexOutOfBound?!</p>

<p>The problem is that the error does not reproduce. I've been able to raise it only once in the dev environment, but trying to reproduce it was not possible (it dit not raise again)... so no way to look for a pattern in the error.</p>

<p>So my only option is simple: read the code and use the brain.</p>

<p>So I browse the code of <code>java.util.ArrayList.get()</code>:</p>

<pre><code>public class ArrayList&lt;E&gt; [...]{
  public E get(int index) {
    RangeCheck(index);
    return (E) elementData[index];
  }
  private void RangeCheck(int index) {
    if (index &gt;= size)
      throw new IndexOutOfBoundsException("Index: "+index+", Size: "+size);
  }
}
</code></pre>

<p>So it throws the exception because <code>index &gt;= size</code>... How is it possible? The <code>for()</code> sweeps from <code>0</code> to <code>size-1</code>... It is impossible! It cannot raise the error!</p>

<p>Wait a second! This code is not thread-safe. Maybe another thread is calling <code>clear()</code> or <code>remove*()</code> on the ArrayList... Studying the code, it is not possible. So I run it, set a breakpoint on line 1944 and watch the threads in that moment, and effectively, the other running threads have nothing to do with this issue.</p>

<p>Any other clue?</p>

<p>Kernnigan &amp; Pike: "Debugging [...]Something impossible occurred, and the only solid information is that it really did occur."</p>
