← Назад к вопросам

Какой исключение появляется при выхода за границы массива?

2.0 Middle🔥 121 комментариев
#Spring Framework

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI22 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Исключение при выходе за границы массива

При попытке доступа к элементу массива по индексу, выходящему за его границы, выбрасывается исключение ArrayIndexOutOfBoundsException. Это одно из самых частых исключений в Java приложениях.

Тип исключения

ArrayIndexOutOfBoundsException — это unchecked exception (исключение, которое не требует явной обработки):

// Иерархия исключения
java.lang.Object
  └── java.lang.Throwable
      └── java.lang.Exception
          └── java.lang.RuntimeException
              └── java.lang.IndexOutOfBoundsException
                  └── java.lang.ArrayIndexOutOfBoundsException

Unchecked vs Checked:

  • Unchecked (наследуется от RuntimeException) — не требует try-catch
  • Checked — требует обработки или объявления в throws

Примеры возникновения

1. Обращение к элементу с индексом >= длины массива

public class ArrayBoundsExample {
    public static void main(String[] args) {
        int[] numbers = {10, 20, 30, 40, 50};
        
        // Длина массива = 5, индексы: 0, 1, 2, 3, 4
        
        // Правильный доступ
        System.out.println(numbers[0]);  // 10 - OK
        System.out.println(numbers[4]);  // 50 - OK (последний элемент)
        
        // Ошибка: индекс 5 не существует
        System.out.println(numbers[5]);  // ArrayIndexOutOfBoundsException: Index 5 out of bounds for length 5
        
        // Ошибка: индекс -1
        System.out.println(numbers[-1]); // ArrayIndexOutOfBoundsException: Index -1 out of bounds for length 5
    }
}

2. Цикл с неправильным условием

public class LoopBoundsError {
    public static void main(String[] args) {
        String[] colors = {"Red", "Green", "Blue"};
        
        // ОШИБКА: i <= colors.length
        for (int i = 0; i <= colors.length; i++) {
            System.out.println(colors[i]);  
            // ArrayIndexOutOfBoundsException на последней итерации
        }
        
        // ПРАВИЛЬНО: i < colors.length
        for (int i = 0; i < colors.length; i++) {
            System.out.println(colors[i]);
        }
    }
}

3. Многомерные массивы

public class MultiDimensionalArrayBounds {
    public static void main(String[] args) {
        int[][] matrix = {
            {1, 2, 3},      // строка 0: 3 элемента
            {4, 5, 6},      // строка 1: 3 элемента
            {7, 8, 9}       // строка 2: 3 элемента
        };
        
        // Правильный доступ
        System.out.println(matrix[0][0]);  // 1 - OK
        System.out.println(matrix[2][2]);  // 9 - OK
        
        // Ошибка: нет строки 3
        System.out.println(matrix[3][0]);  
        // ArrayIndexOutOfBoundsException: Index 3 out of bounds for length 3
        
        // Ошибка: нет колонки 3 в строке 0
        System.out.println(matrix[0][3]);
        // ArrayIndexOutOfBoundsException: Index 3 out of bounds for length 3
    }
}

Обработка исключения

Try-Catch блок:

public class ArrayBoundsHandling {
    public static void main(String[] args) {
        int[] data = {100, 200, 300};
        
        try {
            System.out.println("Accessing index 10...");
            int value = data[10];  // Выбросит исключение
            System.out.println("Value: " + value);
        } catch (ArrayIndexOutOfBoundsException e) {
            System.err.println("Error: " + e.getMessage());
            System.err.println("Stack trace:");
            e.printStackTrace();
        } finally {
            System.out.println("Operation completed");
        }
    }
}

Вывод:

Accessing index 10...
Error: Index 10 out of bounds for length 3
Stack trace:
java.lang.ArrayIndexOutOfBoundsException: Index 10 out of bounds for length 3
    at ArrayBoundsHandling.main(ArrayBoundsHandling.java:8)
Operation completed

Предотвращение исключения

1. Проверка перед доступом

public class SafeArrayAccess {
    public static void main(String[] args) {
        int[] numbers = {10, 20, 30};
        int index = 5;
        
        // Проверяем границы
        if (index >= 0 && index < numbers.length) {
            System.out.println("Value: " + numbers[index]);
        } else {
            System.out.println("Index out of bounds: " + index);
        }
    }
}

2. Использование enhanced for loop (for-each)

public class EnhancedForLoop {
    public static void main(String[] args) {
        String[] names = {"Alice", "Bob", "Charlie"};
        
        // Безопасно: автоматически итерирует через все элементы
        for (String name : names) {
            System.out.println(name);
        }
        // Невозможно получить ArrayIndexOutOfBoundsException с for-each
    }
}

3. Использование Collections вместо массивов

import java.util.ArrayList;
import java.util.List;

public class CollectionsVsArrays {
    public static void main(String[] args) {
        // Массив: ручное управление индексами, риск выхода за границы
        int[] array = {1, 2, 3};
        // array[10];  // ArrayIndexOutOfBoundsException
        
        // ArrayList: безопаснее, предоставляет методы для проверки
        List<Integer> list = new ArrayList<>(java.util.Arrays.asList(1, 2, 3));
        
        // Безопасная проверка
        if (list.contains(1)) {
            System.out.println("Found");
        }
        
        // Итерация без риска
        for (Integer value : list) {
            System.out.println(value);
        }
    }
}

Сообщение об ошибке

Сообщение об ошибке содержит полезную информацию:

public class ExceptionMessage {
    public static void main(String[] args) {
        int[] arr = {1, 2, 3, 4, 5};
        
        try {
            int value = arr[10];
        } catch (ArrayIndexOutOfBoundsException e) {
            // Сообщение содержит:
            // 1. Переданный индекс
            // 2. Размер массива
            System.out.println(e.getMessage());
            // Output: Index 10 out of bounds for length 5
        }
    }
}

Отличие от других исключений

public class SimilarExceptions {
    public static void main(String[] args) {
        // ArrayIndexOutOfBoundsException - для массивов
        int[] array = {1, 2, 3};
        try {
            array[5];  // ArrayIndexOutOfBoundsException
        } catch (ArrayIndexOutOfBoundsException e) {
            System.out.println("Array error: " + e.getClass().getSimpleName());
        }
        
        // StringIndexOutOfBoundsException - для строк
        String str = "Hello";
        try {
            char c = str.charAt(10);  // StringIndexOutOfBoundsException
        } catch (StringIndexOutOfBoundsException e) {
            System.out.println("String error: " + e.getClass().getSimpleName());
        }
        
        // IndexOutOfBoundsException - родительский класс для обоих
    }
}

Лучшие практики

1. Используй enhanced for loop

// Рекомендуется
for (String item : items) {
    process(item);
}

// Нужно, если требуется индекс
for (int i = 0; i < items.length; i++) {
    process(items[i]);
}

2. Проверяй границы явно

if (index >= 0 && index < array.length) {
    return array[index];
}

3. Предпочитай Collections

// Для большинства случаев List лучше, чем массив
List<Item> items = new ArrayList<>();
if (items.size() > index) {
    Item item = items.get(index);
}

4. Логируй проблемные случаи

try {
    return array[index];
} catch (ArrayIndexOutOfBoundsException e) {
    log.error("Index {} out of bounds for array of length {}", index, array.length, e);
    throw e;  // или возвращай default значение
}

Заключение

ArrayIndexOutOfBoundsException — это unchecked исключение, выбрасываемое при попытке доступа к элементу массива по индексу, который меньше 0 или больше/равен длине массива. Это исключение легко избежать, используя:

  • Enhanced for loop (for-each)
  • Явную проверку границ перед доступом
  • Collections вместо массивов
  • IDE подсказки и статический анализ кода
Какой исключение появляется при выхода за границы массива? | PrepBro