Quali sono le cause ArrayIndexOutOfBoundsException?
Se si considera una variabile come una "casella" in cui è possibile posizionare un valore, una matrice è una serie di caselle poste una accanto all'altra, in cui il numero di caselle è un numero intero finito ed esplicito.
Creazione di un array come questo:
final int[] myArray = new int[5]
crea una riga di 5 caselle, ognuna contenente un int. Ciascuna delle caselle ha un indice, una posizione nella serie di caselle. Questo indice inizia da 0 e termina in N-1, dove N è la dimensione dell'array (il numero di caselle).
Per recuperare uno dei valori da questa serie di caselle, puoi fare riferimento ad esso attraverso il suo indice, in questo modo:
myArray[3]
Il che ti darà il valore della quarta casella della serie (poiché la prima casella ha un indice 0).
Un ArrayIndexOutOfBoundsExceptionè causato dal tentativo di recuperare una "scatola" che non esiste, passando un indice che è superiore all'indice dell'ultima "scatola", o negativo.
Con il mio esempio corrente, questi frammenti di codice genererebbero tale eccezione:
myArray[5] //tries to retrieve the 6th "box" when there is only 5
myArray[-1] //just makes no sense
myArray[1337] //waay to high
Come evitare ArrayIndexOutOfBoundsException
Per prevenire ArrayIndexOutOfBoundsException, ci sono alcuni punti chiave da considerare:
looping
Quando si esegue il ciclo in un array, assicurarsi sempre che l'indice che si sta recuperando sia strettamente più piccolo della lunghezza dell'array (il numero di caselle). Per esempio:
for (int i = 0; i < myArray.length; i++) {
Notare il <, mai mescolare un =dentro ..
Potresti essere tentato di fare qualcosa del genere:
for (int i = 1; i <= myArray.length; i++) {
final int someint = myArray[i - 1]
Non farlo. Attenersi a quello sopra (se è necessario utilizzare l'indice) e ti farà risparmiare molto dolore.
Ove possibile, utilizzare foreach:
for (int value : myArray) {
In questo modo non dovrai assolutamente pensare agli indici.
Durante il loop, qualunque cosa tu faccia, MAI cambiare il valore dell'iteratore di loop (qui:) i. L'unico posto in cui ciò dovrebbe cambiare valore è quello di mantenere il ciclo attivo. Altrimenti cambiarlo è solo rischiare un'eccezione, e nella maggior parte dei casi non è necessario.
Retrieval / aggiornamento
Quando si recupera un elemento arbitrario dell'array, verificare sempre che sia un indice valido rispetto alla lunghezza dell'array:
public Integer getArrayElement(final int index) {
if (index < 0 || index >= myArray.length) {
return null; //although I would much prefer an actual exception being thrown when this happens.
}
return myArray[index];
}