Обработка исключений
В теме Введение в обработку исключений были рассмотрены некоторые основные моменты обработки исключений. Сейчас более подробно поговорим о других моментах, связанных с обработкой исключений.
Оператор throws
Иногда метод, в котором может генерироваться исключение, сам не обрабатывает это исключение. В этом случае в объявлении метода используется оператор throws , который надо обработать при вызове этого метода. Например, у нас имеется метод вычисления факториала, и нам надо обработать ситуацию, если в метод передается число меньше 1:
public static int getFactorial(int num) throws Exception < if(num<1) throw new Exception("The number is less than 1"); int result=1; for(int i=1; i<=num;i++)< result*=i; >return result; >
С помощью оператора throw по условию выбрасывается исключение. В то же время метод сам это исключение не обрабатывает с помощью try..catch, поэтому в определении метода используется выражение throws Exception .
Теперь при вызове этого метода нам обязательно надо обработать выбрасываемое исключение:
public static void main(String[] args) < try< int result = getFactorial(-6); System.out.println(result); >catch(Exception ex) < System.out.println(ex.getMessage()); >>
Без обработки исключение у нас возникнет ошибка компиляции, и мы не сможем скомпилировать программу.
В качестве альтернативы мы могли бы и не использовать оператор throws, а обработать исключение прямо в методе:
public static int getFactorial(int num) < int result=1; try< if(num<1) throw new Exception("The number is less than 1"); for(int i=1; i<=num;i++)< result*=i; >> catch(Exception ex) < System.out.println(ex.getMessage()); result=num; >return result; >
Обработка ошибок и исключения
2. Коды возврата. Основная идея — в случае ошибки возвращать специальное значение, которое не может быть корректным. Например, если в методе есть операция деления, то придется проверять делитель на равенство нулю. Также проверим корректность аргументов a и b :
Double f(Double a, Double b) < if ((a == null) || (b == null)) < return null; > //. if (Math.abs(b) < EPS) < return null; > else < return a / b; > >
При вызове метода необходимо проверить возвращаемое значение:
Double d = f(a, b); if (d != null) < //. > else < //. >
Минусом такого подхода является необходимость проверки возвращаемого значения каждый раз при вызове метода. Кроме того, не всегда возможно определить тип ошибки.
3.Использовать флаг ошибки: при возникновении ошибки устанавливать флаг в соответствующее значение:
boolean error; Double f(Double a, Double b) < if ((a == null) || (b == null)) < error = true; return null; > //. if (Math.abs(b) < EPS) < error = true; return b; > else < return a / b; > >
error = false; Double d = f(a, b); if (error) < //. > else < //. >
Минусы такого подхода аналогичны минусам использования кодов возврата.
4.Можно вызвать метод обработки ошибки и возвращать то, что вернет этот метод.
Double f(Double a, Double b) < if ((a == null) || (b == null)) < return nullPointer(); > //. if (Math.abs(b) < EPS) < return divisionByZero(); > else < return a / b; > >
Но в таком случае не всегда возможно проверить корректность результата вызова основного метода.
5.В случае ошибки просто закрыть программу.
if (Math.abs(b) < EPS) < System.exit(0); return this; >
Это приведет к потере данных, также невозможно понять, в каком месте возникла ошибка.
Исключения
В Java возможна обработка ошибок с помощью исключений:
Double f(Double a, Double b) < if ((a == null) || (b == null)) < throw new IllegalArgumentException("arguments of f() are null"); > //. return a / b; >
Проверять b на равенство нулю уже нет необходимости, так как при делении на ноль метод бросит непроверяемое исключение ArithmeticException .
- разделить обработку ошибок и сам алгоритм;
- не загромождать код проверками возвращаемых значений;
- обрабатывать ошибки на верхних уровнях, если на текущем уровне не хватает данных для обработки. Например, при написании универсального метода чтения из файла невозможно заранее предусмотреть реакцию на ошибку, так как эта реакция зависит от использующей метод программы;
- классифицировать типы ошибок, обрабатывать похожие исключения одинаково, сопоставлять специфичным исключениям определенные обработчики.
Каждый раз, когда при выполнении программы происходит ошибка, создается объект-исключение, содержащий информацию об ошибке, включая её тип и состояние программы на момент возникновения ошибки. После создания исключения среда выполнения пытается найти в стеке вызовов метод, который содержит код, обрабатывающий это исключение. Поиск начинается с метода, в котором произошла ошибка, и проходит через стек в обратном порядке вызова методов. Если не было найдено ни одного подходящего обработчика, выполнение программы завершается.
Таким образом, механизм обработки исключений содержит следующие операции:
- Создание объекта-исключения.
- Заполнение stack trace’а этого исключения.
- Stack unwinding (раскрутка стека) в поисках нужного обработчика.
Классификация исключений
Класс Java Throwable описывает все, что может быть брошено как исключение. Наследеники Throwable — Exception и Error — основные типы исключений. Также RuntimeException , унаследованный от Exception , является существенным классом.
Иерархия стандартных исключений
Проверяемые исключения
Наследники класса Exception (кроме наслеников RuntimeException ) являются проверяемыми исключениями(checked exception). Как правило, это ошибки, возникшие по вине внешних обстоятельств или пользователя приложения – неправильно указали имя файла, например. Эти исключения должны обрабатываться в ходе работы программы, поэтому компилятор проверяет наличие обработчика или явного описания тех типов исключений, которые могут быть сгенерированы некоторым методом.
Все исключения, кроме классов Error и RuntimeException и их наследников, являются проверяемыми.
Error
Класс Error и его подклассы предназначены для системных ошибок. Свои собственные классы-наследники для Error писать (за очень редкими исключениями) не нужно. Как правило, это действительно фатальные ошибки, пытаться обработать которые довольно бессмысленно (например OutOfMemoryError ).
RuntimeException
Эти исключения обычно возникают в результате ошибок программирования, такие как ошибки разработчика или неверное использование интерфейса приложения. Например, в случае выхода за границы массива метод бросит OutOfBoundsException . Такие ошибки могут быть в любом месте программы, поэтому компилятор не требует указывать runtime исключения в объявлении метода. Теоретически приложение может поймать это исключение, но разумнее исправить ошибку.
Обработка исключений
Чтобы сгенерировать исключение используется ключевое слово throw . Как и любой объект в Java, исключения создаются с помощью new .
if (t == null) < throw new NullPointerException("t = null"); >
Есть два стандартных конструктора для всех исключений: первый — конструктор по умолчанию, второй принимает строковый аргумент, поэтому можно поместить подходящую информацию в исключение.
Возможна ситуация, когда одно исключение становится причиной другого. Для этого существует механизм exception chaining. Практически у каждого класса исключения есть конструктор, принимающий в качестве параметра Throwable – причину исключительной ситуации. Если же такого конструктора нет, то у Throwable есть метод initCause(Throwable) , который можно вызвать один раз, и передать ему исключение-причину.
Как и было сказано раньше, определение метода должно содержать список всех проверяемых исключений, которые метод может бросить. Также можно написать более общий класс, среди наследников которого есть эти исключения.
void f() throws InterruptedException, IOException < //.
try-catch-finally
Код, который может бросить исключения оборачивается в try -блок, после которого идут блоки catch и finally (Один из них может быть опущен).
try < // Код, который может сгенерировать исключение >
Сразу после блока проверки следуют обработчики исключений, которые объявляются ключевым словом catch.
try < // Код, который может сгенерировать исключение > catch(Type1 id1) < // Обработка исключения Type1 > catch(Type2 id2) < // Обработка исключения Type2 >
Сatch -блоки обрабатывают исключения, указанные в качестве аргумента. Тип аргумента должен быть классом, унаследованного от Throwable , или самим Throwable . Блок catch выполняется, если тип брошенного исключения является наследником типа аргумента и если это исключение не было обработано предыдущими блоками.
Код из блока finally выполнится в любом случае: при нормальном выходе из try , после обработки исключения или при выходе по команде return .
NB: Если JVM выйдет во время выполнения кода из try или catch , то finally -блок может не выполниться. Также, например, если поток выполняющий try или catch код остановлен, то блок finally может не выполниться, даже если приложение продолжает работать.
Блок finally удобен для закрытия файлов и освобождения любых других ресурсов. Код в блоке finally должен быть максимально простым. Если внутри блока finally будет брошено какое-либо исключение или просто встретится оператор return , брошенное в блоке try исключение (если таковое было брошено) будет забыто.
import java.io.IOException; public class ExceptionTest < public static void main(String[] args) < try < try < throw new Exception("a"); > finally < throw new IOException("b"); > > catch (IOException ex) < System.err.println(ex.getMessage()); > catch (Exception ex) < System.err.println(ex.getMessage()); > > >
После того, как было брошено первое исключение — new Exception(«a») — будет выполнен блок finally , в котором будет брошено исключение new IOException(«b») , именно оно будет поймано и обработано. Результатом его выполнения будет вывод в консоль b . Исходное исключение теряется.
Обработка исключений, вызвавших завершение потока
При использовании нескольких потоков бывают ситуации, когда поток завершается из-за исключения. Для того, чтобы определить с каким именно, начиная с версии Java 5 существует интерфейс Thread.UncaughtExceptionHandler . Его реализацию можно установить нужному потоку с помощью метода setUncaughtExceptionHandler . Можно также установить обработчик по умолчанию с помощью статического метода Thread.setDefaultUncaughtExceptionHandler .
Интерфейс Thread.UncaughtExceptionHandler имеет единственный метод uncaughtException(Thread t, Throwable e) , в который передается экземпляр потока, завершившегося исключением, и экземпляр самого исключения. Когда поток завершается из-за непойманного исключения, JVM запрашивает у потока UncaughtExceptionHandler , используя метод Thread.getUncaughtExceptionHandler() , и вызвает метод обработчика – uncaughtException(Thread t, Throwable e) . Все исключения, брошенные этим методом, игнорируются JVM.
Информация об исключениях
- getMessage() . Этот метод возвращает строку, которая была первым параметром при создании исключения;
- getCause() возвращает исключение, которое стало причиной текущего исключения;
- printStackTrace() печатает stack trace, который содержит информацию, с помощью которой можно определить причину исключения и место, где оно было брошено.
Exception in thread "main" java.lang.IllegalStateException: A book has a null property at com.example.myproject.Author.getBookIds(Author.java:38) at com.example.myproject.Bootstrap.main(Bootstrap.java:14) Caused by: java.lang.NullPointerException at com.example.myproject.Book.getId(Book.java:22) at com.example.myproject.Author.getBookIds(Author.java:35)
Все методы выводятся в обратном порядке вызовов. В примере исключение IllegalStateException было брошено в методе getBookIds , который был вызван в main . «Caused by» означает, что исключение NullPointerException является причиной IllegalStateException .
Разработка исключений
Чтобы определить собственное проверяемое исключение, необходимо создать наследника класса java.lang.Exception . Желательно, чтобы у исключения был конструкор, которому можно передать сообщение:
public class FooException extends Exception < public FooException() < super(); > public FooException(String message) < super(message); > public FooException(String message, Throwable cause) < super(message, cause); > public FooException(Throwable cause) < super(cause); > >
Исключения в Java7
- обработка нескольких типов исключений в одном catch -блоке:
catch (IOException | SQLException ex)
В таких случаях параметры неявно являются final , поэтому нельзя присвоить им другое значение в блоке catch .
Байт-код, сгенерированный компиляцией такого catch -блока будет короче, чем код нескольких catch -блоков.
- Try с ресурсами позволяет прямо в try -блоке объявлять необходимые ресурсы, которые по завершению блока будут корректно закрыты (с помощью метода close() ). Любой объект реализующий java.lang.AutoCloseable может быть использован как ресурс.
static String readFirstLineFromFile(String path) throws IOException < try (BufferedReader br = new BufferedReader(new FileReader(path))) < return br.readLine(); > >
В приведенном примере в качестве ресурса использутся объект класса BufferedReader , который будет закрыт вне зависимосити от того, как выполнится try -блок.
Можно объявлять несколько ресурсов, разделяя их точкой с запятой:
public static void viewTable(Connection con) throws SQLException < String query = "select COF_NAME, SUP_ID, PRICE, SALES, TOTAL from COFFEES"; try (Statement stmt = con.createStatement(); ResultSet rs = stmt.executeQuery(query)) < //Work with Statement and ResultSet > catch (SQLException e) < e.printStackTrace; >>
Во время закрытия ресурсов тоже может быть брошено исключение. В try-with-resources добавленна возможность хранения «подавленных» исключений, и брошенное try -блоком исключение имеет больший приоритет, чем исключения получившиеся во время закрытия. Получить последние можно вызовом метода getSuppressed() от исключения брошенного try -блоком.
- Перебрасывание исключений с улучшенной проверкой соответствия типов.
Компилятор Java SE 7 тщательнее анализирует перебрасываемые исключения. Рассмотрим следующий пример:
static class FirstException extends Exception < >static class SecondException extends Exception < >public void rethrowException(String exceptionName) throws Exception < try < if ("First".equals(exceptionName)) < throw new FirstException(); > else < throw new SecondException(); > > catch (Exception ex) < throw e; > >
В примере try -блок может бросить либо FirstException , либо SecondException . В версиях до Java SE 7 невозможно указать эти исключения в декларации метода, потому что catch -блок перебрасывает исключение ex , тип которого — Exception .
В Java SE 7 вы можете указать, что метод rethrowException бросает только FirstException и SecondException . Компилятор определит, что исключение Exception ex могло возникнуть только в try -блоке, в котором может быть брошено FirstException или SecondException . Даже если тип параметра catch — Exception , компилятор определит, что это экземпляр либо FirstException , либо SecondException :
public void rethrowException(String exceptionName) throws FirstException, SecondException < try < // . > catch (Exception e) < throw e; > >
Если FirstException и SecondException не являются наследниками Exception , то необходимо указать и Exception в объявлении метода.
Примеры исключений
- любая операция может бросить VirtualMachineError . Как правило это происходит в результате системных сбоев.
- OutOfMemoryError . Приложение может бросить это исключение, если, например, не хватает места в куче, или не хватает памяти для того, чтобы создать стек нового потока.
- IllegalArgumentException используется для того, чтобы избежать передачи некорректных значений аргументов. Например:
public void f(Object a) < if (a == null) < throw new IllegalArgumentException("a must not be null"); > >
- IllegalStateException возникает в результате некорректного состояния объекта. Например, использование объекта перед тем как он будет инициализирован.
Гарантии безопасности
При возникновении исключительной ситуации, состояния объектов и программы могут удовлетворять некоторым условиям, которые определяются различными типами гарантий безопасности:
- Отсутствие гарантий (no exceptional safety). Если было брошено исключение, то не гарантируется, что все ресурсы будут корректно закрыты и что объекты, методы которых бросили исключения, могут в дальнейшем использоваться. Пользователю придется пересоздавать все необходимые объекты и он не может быть уверен в том, что может переиспозовать те же самые ресурсы.
- Отсутствие утечек (no-leak guarantee). Объект, даже если какой-нибудь его метод бросает исключение, освобождает все ресурсы или предоставляет способ сделать это.
- Слабые гарантии (weak exceptional safety). Если объект бросил исключение, то он находится в корректном состоянии, и все инварианты сохранены. Рассмотрим пример:
class Interval < //invariant: left double left; double right; //. >
Если будет брошено исключение в этом классе, то тогда гарантируется, что ивариант «левая граница интервала меньше правой» сохранится, но значения left и right могли измениться.
- Сильные гарантии (strong exceptional safety). Если при выполнении операции возникает исключение, то это не должно оказать какого-либо влияния на состояние приложения. Состояние объектов должно быть таким же как и до вызовов методов.
- Гарантия отсутствия исключений (no throw guarantee). Ни при каких обстоятельствах метод не должен генерировать исключения. В Java это невозможно, например, из-за того, что VirtualMachineError может произойти в любом месте, и это никак не зависит от кода. Кроме того, эту гарантию практически невозможно обеспечить в общем случае.
Источники
- Обработка ошибок и исключения — Сайт Георгия Корнеева
- Лекция Георгия Корнеева — Лекториум
- The Java Tutorials. Lesson: Exceptions
- Обработка исключений — Википедия
- Throwable (Java Platform SE 7 ) — Oracle Documentation
- try/catch/finally и исключения — www.skipy.ru
Как бросить исключение java
Для бросания исключения в Java нужно использовать оператор throw . Он позволяет явно сгенерировать исключение в любом месте кода.
public void divide(int a, int b) throws ArithmeticException if (b == 0) throw new ArithmeticException("Деление на ноль"); > int result = a / b; System.out.println("Результат: " + result); >
В этом примере мы проверяем, равен ли делитель b нулю, и если да, то мы бросаем новое исключение типа ArithmeticException с сообщением «Деление на ноль».
Когда исключение брошено, код в методе останавливается, и контроль передается обработчику исключений или вызывающему методу, который должен перехватить и обработать исключение.
Исключения в Java — пояснение и примеры

Исключение – это нежелательная ситуация, которая возникает во время выполнения программы и нарушает нормальный ход ее работы.
Курс Англійської.
Вивчай англійську прямо зі свого смартфона за допомоги смарт-платформи.

Такая ситуация может возникнуть, например, при попытке чтения из несуществующего файла, делении на ноль, сбое устройства и так далее. Исключение можно перехватить, чтобы принять соответствующие меры.
Приведем пример кода, в котором возникает исключение.
class ExceptionTest < // Метод принимает два целых числа // и возвращает результат деления // первого на второе static float divide(int x, int y)< float result = x / y; return result; >public static void main(String args[]) < // Эта строка будет выполнена System.out.println(divide(4, 2)); // Эта тоже System.out.println(divide(0, 2)); // Эта выбросит исключение System.out.println(divide(4, 0)); >>
Если его запустить, получим следующий вывод:
Курс Англійської.
Онлайн-навчання англійської за методикою Кембриджу — вибір понад мільярда людей.
2.0 0.0 Exception in thread "main" java.lang.ArithmeticException: / by zero at ExceptionTest.divide(ExceptionTest.java:6) at ExceptionTest.main(ExceptionTest.java:16)
Выводятся два результата деления и сообщение об исключении. В этом сообщении указана следующая информация:
- тип исключения (ArithmeticException);
- какое именно исключение возникло (деление на ноль);
- стек выполнения: методы и строки, в которых возникло исключение.

Курсы по изучению Java от наших друзей Mate Academy и Hillel, помогут вам разобраться не только в основах языка программирования, но и в тонкостях работы с ним.
Операторы try, catch, finally, throw, throws: обработка исключений и примеры использования
Для перехвата исключительных ситуаций создается объект исключения, который передается среде выполнения. Он содержит информацию об ошибке, в том числе ее тип и состояние программы на момент возникновения ошибки. Создание объекта исключения и его передача среде выполнения называется выбрасыванием исключительной ситуации.
try-catch
Для перехвата исключения используется конструкция try – catch . Код, который нужно проверить на исключение, заключается в блок try, а код, обрабатывающий исключение – в блок catch.
Добавим эти блоки в приведенный выше блок кода и дополним его парой переменных для наглядности.
Курс Python.
Цю мову програмування використовують від базових концепцій до складних застосувань у сферах штучного інтелекту. Після проходження курсу гарантовано отримай роботу в ІТ.
class ExceptionTest < // Метод принимает два целых числа // и возвращает результат деления // первого на второе static float divide(int x, int y)< float result = x / y; return result; >public static void main(String args[]) < int x = 4; int y = 2; try < // Эта строка будет выполнена System.out.println(divide(x, y)); x = 0; // Эта тоже System.out.println(divide(x, y)); x = 4; y = 0; // Эта выбросит исключение System.out.println(divide(x, y)); >catch (ArithmeticException e) < System.out.println("Ошибка при делении " + x + " на " + y); >> >
Получим более удобочитаемый вывод:
2.0 0.0 Ошибка при делении 4 на 0
finally
Блок finally выполняется после try-catch, независимо от того, возникло ли исключение. Это необязательный блок, но если нет блока catch, то блок finally необходим.
В этом блоке можно, например, закрыть файл, открытый в блоке try, как в приведенном ниже коде.
import java.io.FileWriter; import java.io.IOException; public class FinallyTest < public static void main(String[] args) < FileWriter writer = null; try < writer = new FileWriter("out.txt"); writer.write("Writing to the file!"); System.out.println("Файл записан успешно."); >catch (IOException e) < System.out.println("Ошибка записи в файл."); e.printStackTrace(); >finally < if ( writer != null )< try< writer.close(); >catch (IOException e) < System. out.println("Ошибка закрытия файла."); e.printStackTrace(); >> > > >
throw
В некоторых случаях требуется выбросить исключение самостоятельно. Это делается при помощи ключевого слова throw .
В данном примере метод PrintMe выбрасывает исключение, если его аргумент равен null.
import java.util.LinkedList; public class ThrowTest < public static void main(String[] args) < LinkedListfruits = new LinkedList(); fruits.add("apple"); fruits.add("banana"); fruits.add("orange"); fruits.add("mango"); // Печатает список ThrowTest.PrintMe(fruits); // Выбрасывает исключение ThrowTest.PrintMe(null); > public static void PrintMe(LinkedList fruits) < if (fruits == null)< throw new NullPointerException("Аргумент не инициализирован"); >System.out.println(fruits); > >
throws
Ключевое слово throws используется, чтобы в сигнатуре метода указать, что он выбрасывает исключение. Его можно использовать, чтобы передавать исключения по стеку вызовов и указать, что эти исключения не обязательно должны обрабатываться в методе, в котором они объявлены.
import java.io.BufferedReader; import java.io.FileReader; import java.io.IOException; public class ThrowsTest < public static void readFromFile() throws IOException < // Указываем несуществующий файл, чтобы проверить работу исключения try (BufferedReader reader = new BufferedReader(new FileReader("out.txt"))) < String line; while ((line = reader.readLine()) != null) < System.out.println(line + "\n"); >> > public static void main(String[] args) < try < readFromFile(); >catch (IOException ioe) < System.out.println("Файл не найден"); >> >

Иерархия исключений Java
Исключения в Java делятся на две основные категории: встроенные и пользовательские.
Встроенные исключения
Встроенные исключения – это исключения, которые заранее определены в Java.
Курс Front-end Basic.
Оволодій навичками розробки веб-інтерфейсів та стань справжнім Front-end розробником! Заробляй від 800$ на початку карʼєри.
Когда возникает встроенное исключение, виртуальная машина Java (JVM) создает объект, принадлежащий классу встроенного исключения. Все исключения происходят от класса java.lang.Throwable, но они определены в нескольких пакетах.

Класс Throwable происходит непосредственно об класса Object и является корневым классом дерева классов исключений. От него происходят два подкласса: Error и Exception. Ошибки и исключения, которые встречаются в программах на Java, являются объектами этих классов.
С использованием класса Throwable можно создавать собственные исключения.
Класс Error является надклассом для всех классов ошибок времени выполнения. Он завершает выполнение программы, если происходит ошибка, связанная с системой или ресурсами (JVM).
Ошибки обычно представляют собой необычную проблему, после которой сложно произвести восстановление. Они происходят не по вине программиста, а из-за ненадлежащей работы системы или выделения ресурсов.
Примеры ошибок: AssertionError, LinkageError, OutOfMmeoryError, StackOverFlowError, VirtualMachineError.
Класс Exception представляет ошибки, вызванные программой или внешними факторами. Это надкласс для все классов исключений.
Для этого класса существует два конструктора:
- public Exception() (по умолчанию)
- public Exception(String message) (принимает строковое сообщение как аргумент)
Эти конструкторы наследуются всеми подклассами исключений. Сам по себе класс Exception не предоставляет собственных методов. Он наследует методы класса Throwable.
Встроенные исключения делятся на две группы: проверяемые (checked) и непроверяемые (unchecked).

Проверяемые исключения в Java
Проверяемые исключения проверяются компилятором Java во время компиляции и не являются подклассами RuntimeException (исключения времени выполнения).
Если метод выбрасывает проверяемое исключение, то это исключение необходимо обработать либо в этом же методе, либо передать вызывающему методу.
Проверяемые исключения обрабатываются либо в блоке try-catch, либо в объявлении метода с ключевым словом throws. Если исключение не обработано, происходит ошибка компиляции.
Проверяемыми исключениями являются все исключения, кроме RuntimeException, Error и их подклассов.
Примеры проверяемых исключений: ClassNotFoundException, IOException, SQLException, IllegalAccessException, FileNotFoundException.
Непроверяемые исключения (исключения времени выполнения) в Java
Непроверяемые исключения в Java – это исключения, которые проверяются JVM, а не компилятором Java. Они возникают во время выполнения программы.
Все подклассы RuntimeException называются непроверяемыми исключениями или исключениями времени выполнения в Java.
Можно написать программу на Java и скомпилировать ее, но мы не увидим непроверяемых исключений и ошибок, пока не запустим эту программу.
Компилятор Java не проверяет исключения времени выполнения во время компиляции, независимо от того, обрабатывает ли их программа.
Если в методе возникает исключение времени выполнения, а программист не обрабатывает его, JVM прекращает выполнение программы, не выполняя остаток кода.
Примеры непроверяемых исключений: ArithmeticException, ArrayIndexOutOfBoundsException, ClassCastException, NegativeArraySizeException, NullPointerException.

В Java определено множество встроенных исключений. Ниже приведены описания некоторых из них.
| Исключение | Описание |
| ArithmeticException | Выбрасывается, когда возникает исключительная арифметическая ситуация. |
| ArrayIndexOutOfBoundsException | Выбрасывается при попытке обратиться к массиву по недействительному индексу. |
| ArrayStoreException | Выбрасывается при попытке сохранить объект несоответствующего типа в массиве объектов. |
| ClassCastException | Выбрасывается, когда код совершает попытку привести тип объекта к подклассу, экземпляром которого он не является. |
| ClassNotFoundException | Выбрасывается, когда приложение совершает попытку загрузить класс по его имени в строковом представлении с использованием метода forName в классе Class. |
| CloneNotSupportedException | Выбрасывается, когда для клонирования объекта определенного класса вызван метод clone, но класс этого объекта не реализует интерфейс Cloneable. |
| EnumConstantNotPresentException | Выбрасывается, когда приложение производит попытку обратиться к константе из перечисления по имени, но тип этого перечисления не содержит константу с указанным именем. |
| Exception | Класс Exception и его подклассы являются подклассами Throwable и указывают на ситуации, которые могут быть перехвачены приложением. |
| IllegalAccessException | Выбрасывается, когда приложение совершает попытку применить рефлексию, чтобы создать экземпляр (отличный от массива), присвоить полю значение или получить значение поля, вызвать метод, но текущий выполняемый метод не имеет доступа к определению указанного класса, поля, метода или конструктора. |
| IllegalArgumentException | Выбрасывается, когда методу передан недопустимый или неприемлемый аргумент. |
| IllegalMonitorStateException | Выбрасывается, когда нить пытается ожидать монитор объекта или отправить оповещение другим нитям, ожидающим монитор объекта, но указанный монитор не принадлежит ей. |
| IllegalStateException | Выбрасывается, когда метод вызван в недопустимое или неприемлемое время. |
| IllegalThreadStateException | Выбрасывается, когда нить находится в неприемлемом состоянии для выполнения запрошенной операции. |
| IndexOutOfBoundsException | Выбрасывается, когда индекс определенного типа (например, для массива, строки или вектора) находится вне допустимого диапазона. |
| InstantiationException | Выбрасывается, когда приложение совершает попытку создать экземпляр класса с использованием метода newInstance класса Class, но создать экземпляр указанного класса невозможно. |
| InterruptedException | Выбрасывается, когда нить находится в состоянии ожидания, сна или занята каким-либо другим образом, но ее работа прервана либо перед выполнением действия, либо после его выполнения. |
| NegativeArraySizeException | Выбрасывается, когда приложение совершает попытку создать массив отрицательного размера. |
| NoSuchFieldException | Выбрасывается, когда в классе отсутствует поле с указанным именем. |
| NoSuchMethodException | Выбрасывается, когда невозможно найти указанный метод. |
| NullPointerException | Выбрасывается, когда приложение совершает попытку использовать значение null, но требуется указать объект. |
| NumberFormatException | Выбрасывается, когда приложение совершает попытку преобразовать строку в один из числовых типов, но строка имеет недопустимый формат. |
| RuntimeException | Это родительский класс для тех исключений, которые могут быть выброшены при нормальной работе виртуальной машины Java. |
| SecurityException | Выбрасывается менеджером безопасности при нарушении безопасности. |
| StringIndexOutOfBoundsException | Выбрасывается методами класса String при попытке использовать отрицательный индекс или индекс, превышающий размер строки. |
| TypeNotPresentException | Выбрасывается, когда приложение совершает попытку доступа к типу с указанием его имени в виде строки, но не удается найти определение типа с указанным именем. |
| UnsupportedOperationException | Выбрасывается, когда запрошенная операция не поддерживается. |
Пользовательские исключения
Пользовательские исключения создаются пользователями или программистами в соответствии с их собственными потребностями. Они создаются путем расширения класса Exception.
Примером пользовательского исключения может служить исключение, выбрасываемое, если пользователь пытается открыть банковский счет, но не достиг возраста 18 лет. В таком случае может быть выдано сообщение о том, что требуется открыть счет с кем-то из родителей.
Чтобы использовать пользовательское исключение, нужно выполнить следующие действия.
- Определить класс, расширяющий класс Exception.
- Определить конструктор. Если не требуется хранить сведения об исключении, определяется конструктор по умолчанию. Если требуется сохранить сведения об исключении в виде строки, определяется конструктор с параметром.
- Создать объект пользовательского исключения и выбросить его с помощью ключевого слова throw.
Пример исключения с конструктором по умолчанию:
class MyException extends Exception < // Конструктор по умолчанию MyException()<>> class Main < public static void main(String[] args)< try< MyException e = new MyException(); throw e; >catch(MyException ex) < System.out.println("Перехвачено пользовательское исключение"); >> >
Этот код выведет следующий текст: “ Перехвачено пользовательское исключение”.
Пример исключения с параметром в конструкторе:
class MyException extends Exception < MyException(String msg)< super(msg); >> class Main < public static void main(String[] args)< try< MyException e = new MyException("Перехвачено пользовательское исключение с информацией"); throw e; >catch(MyException ex) < System.out.println(ex.getMessage()); >> >
Вывод будет таким: “ Перехвачено пользовательское исключение с информацией”
Заключение
Исключения в Java позволяют указать пути обхода проблем и исправления их последствий. С их помощью можно поместить логику обработки исключительных ситуаций в отдельные блоки кода (catch), оставив основную логику в блоке try, а логику завершающих действий по обработке исключения – в блоке finally. Исключения могут быть обработаны в методах, где они возникают, или переданы далее с помощью ключевых throw и throws.
Java предоставляет обширный набор встроенных исключений, а также дает программисту гибкость, позволяя создавать собственные исключения в соответствии с потребностями приложения.
