Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
кпп.docx
Скачиваний:
0
Добавлен:
01.07.2025
Размер:
238.24 Кб
Скачать

Классификация исключений.

На вершине иерархии находится класс Throwable. Все классы исключений являются производными от него. Среди наследников этого класса можно выделить две ветви – Error и Exeption. Класс Error описывает различные ошибки и сбои в системе, нехватку ресурсов, аппаратные проблеммы. Самостоятельно сгенерировать исключение этого класса невозможно. В некоторых случаях при ошибках этого типа программа имеет возможность выдать диагностическое сообщение и корректно завершиться, но далеко не всегда.

 Потомки другой ветви, - класса Exception, бывают двух видов.

Класс RuntimeException – исключения этого типа возникают вследствие программистских ошибок (например, неверное приведение типов, выход за пределы массива, попытка обратиться к объекту по пустой ссылке null и т.д.).

 Класс IOException – обрабатывает ошибки различных штатных ситуаций, не связанные с ошибками выполнения, например, ошибки ввода/вывода, попытка чтения после конца файла, попытка получить объект несуществующего класса, ошибки инициализации сокетного соединения и т.д.).

 Таким образом, все исключения подразделяются на две большие группы – проверяемые и непроверяемые. Проверяемые исключения проверяются компилятором и для этого типа исключений обязательна обработка в том или ином виде. Непроверяемые исключения компилятором не отслеживаются и не проверяются, они обрабатываются программным обеспечением JVM, поэтому их обработка в коде программы нежелательна.

К непроверяемым исключениям относятся исключения классов Runtime Exception и его подклассов, а также класса Error и его подклассов.

Все остальные исключения являются проверяемыми. Классов-исключений в java довольно много, более двухсот в различных пакетах, поэтому программист всегда может подобрать для своей конкретной цели подходящий класс исключений.

Перехват исключений блоками try/catch.

Писать код вида:

 if(какая – то "опасная" инструкция) { обработка исключения… }

 Не слишком рационально, поскольку в этом случае вся программа будет состоять из одних только if-ов, проверяющих различные возвращаемые значения. В каких – то случаях это оправдано, например, при ошибках ввода – вывода, когда операторы записи в файл в случае неудачи, возвращают "-1". А в каких – то нет, поскольку никаких проверяемых значений не возвращается, например при сбоях в памяти или выходе за пределы массива. Поэтому для ловли исключений придуман специальный унифицированный механизм. Рассмотрим пример использования оператора try/catch:

 int a = 0;

try {

             double b =  1/a;

 } catch (Throwable e) {

 System.out.println("исключение обработано!");

             System.out.println(e);

}

 Мы охватываем "опасную" инструкцию блоком try/catch, в котором объявляем экземпляр класса Throwable. Это родительский класс для всего семейства классов исключений, поэтому все возбуждаемые исключения обрабатываются в первую очередь именно им.

В консоли будет напечатано:

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

java.lang.ArithmeticException: / by zero

 

 Т.е. исключение может быть обработано конкретным классом ArithmeticException, тип исключения деление на 0.

Поменяем экземпляр класса Throwable на класс Error. И перезапустим программу. В консоли появится сообщение:

 Exception in thread "main" java.lang.ArithmeticException: / by zero

            at welkom.Welkom.main(Welkom.java:27)

Java Result: 1

 Т. е. Наш код уже не выполняется, а исключение нишим блоком  try/catch  не перехватывается и не обрабатывается. Происходит это потому, что исключение обрабатывается другой ветвью классов – наследников, а мы объявили в блоке catch (Error e) … класс исключений совсем другого типа.

Экспериментируем дальше. Заменяем в блоке try/catch  класс исключения вначале на общий …

 } catch(Exception e) {

 Сообщение выводится:

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

java.lang.ArithmeticException: / by zero

 Затем на:

} catch(RuntimeException e) {

 Сообщение выводится. И наконец, на:

 …

} catch(IOException e) {

… 

Так как исключения типа IOException относятся к проверяемым, компилятор будет возмущаться, сообщая нам, что такое исключение здесь никогда возникнуть не может. Поэтому усыпляем его бдительность добавлением незначащего кода, в котором такое исключение возможно:

 import java.io.IOException;        // не забудьте импортировать соответствующие классы...

import java.io.File;

int a = 0;

        try {

           File  my_file  =  new File("readme.txt");   // незначащий код

           Boolean  success  =  my_file.createNewFile();   // незначащий код

         double b  =  1/a;  

                   } catch(IOException e) {

             System.out.println("исключение обработано!");

             System.out.println(e);

        }

 После запуска программы будет выведено:

 Exception in thread "main" java.lang.ArithmeticException: / by zero

            at welkom.Welkom.main(Welkom.java:27)

Java Result: 1

 Наше сообщение не выводится, как и ожидалось, а само исключение, возбуждаемое делением на ноль классами ветви IOException не обрабатывается.

Таким образом, как мы видим,  эти типы исключений обрабатываются цепочкой Throwable -> Exception ->RuntimeException и производными от них классами.

Если мы не объявляем экземпляр какого – либо из этих классов в своей программе, мы не можем перехватить и обработать это исключение и исключение обрабатывается стандартным способом без нашего участия.

 Конструкция try/catch  имеет дополнение finally. То есть полная сигнатура может выглядеть как: 

try  {

} catch  (...)  {

} finally {

}

 Если блок finally присутствует, он вызывается в обязательном порядке после блока catch. В блоке finally можно написать какие-либо действия, которые программа будет выполнять после обработки исключения, например, закрывать открытые файлы, сохранять результаты работы на диск или сохранять в лог причину ошибки. Если этот блок присутствует, то блока catch может не быть. В этом случае мы отказываемся от обработки исключения, но имеем возможность при его возникновении все же выполнить какие – либо действия.