Слайд 1Программирование
Тема 5 Обработка исключений в С++, Java и C#
Слайд 2 Обработка исключений в C++
Операторы для работы с
исключениями
try { /*контролируемый блок*/
[ throw выражение; ]
}
catch (тип параметра имя параметра)
{ /* блок обработки */ }
catch (тип параметра)
{ /* блок обработки */ }
catch (…)
{ /* блок обработки */ }
Слайд 3 Обработка исключений в C++
Исключения, или исключительные ситуации - это
события, нарушающие нормальный ход выполнения программы.
Наиболее часто встречаются следующие исключения:
нехватка памяти, выход индекса за границы массива, арифметическое переполнение, деление на ноль, недопустимые параметры функций.
в С++ для работы с исключениями используются следующие операторы: try (контролировать), throw (выбрасывать), catch (перехватывать). Синтаксис записи операторов показан на слайде 2.
Оператор try выделяет часть программы, в которой может возникнуть исключение.
Когда при выполнении программы происходит исключительная ситуация, то программа должна создать специальный объект-исключение. Объект-исключение часто называют просто исключением, а процесс его создания выбрасыванием исключения (exception throwing).
Исключения могут выбрасываться автоматически (неявно) в случае их возникновения. В этом случае создаются объекты-исключения стандартных классов исключений. Также исключения можно явно выбрасывать с помощью оператора throw. Выражение, стоящее после ключевого слова throw на практике означает, либо константу, либо переменную некоторого типа. Тип может быть любым (встроенным или пользовательским). Часто после ключевого слова throw указывают объект класса исключения (стандартного или пользовательского).
Исключение может выбрасываться в функциях, прямо или косвенно вложенных в try-блок. Контролируемый блок, помимо функции контроля, обладает функциями обычного блока: все переменные, объявленные внутри него, являются локальными в этом блоке и не видны вне его.
После блока try обязательно прописывается один или несколько операторов catch.
Оператор catch определяет обработчик исключения, которому передается управление в случае возникновения исключения. Управление передается тому обработчику тип параметра которого совпадает с типом объекта-исключения. Если на месте параметра в обработчике catch написано многоточие, то такой обработчик перехватывает все исключения. Оператор catch с параметром-многоточием всегда должен быть последним.
Слайд 4 Обработка исключений в C++
Варианты создания объекта класса
исключения
try { …
if (/*условие возникновения исключения*/)
{ TException e; //создание объекта e класса
// исключения TException
throw ex;
или
throw TException(); //создание безымянного
// объекта класса исключения TException
}
}
Способы передачи объекта класса исключения в обработчик:
catch (TException e) // по значению
catch (TException& e) // по ссылке
catch (const TException& e) // по конст. ссылке
catch (TException *e) // по указателю
catch (const TException *e) // по конст. указателю
Слайд 5 Обработка исключений в C++
В С++ порождаемое исключение может быть
константой или переменной любого встроенного или пользовательского типа, но чаще
всего – это объект класса исключения.
На слайде 4 показаны способы создания объекта класса исключения и способы передачи объекта класса исключения в обработчик.
Работа конструкции try...catch напоминает работу оператора switch. Операторы обработчики похожи на альтернативы case, а блок catch с многоточием соответствует альтернативе default оператора-переключателя. Если в блоке try возникает исключение, то начинается сравнение типа сгенерированного исключения и типов параметров в секциях-обработчиках. Выполняется тот блок catch, тип параметра которого совпал с типом исключения. Если такого типа не найдено, выполняется блок catch с многоточием. Если же такого блока в текущем списке обработчиков не обнаруживается, то ищется другой список обработчиков в вызывающей функции. Этот поиск продолжается вплоть до функции main(). Если же и там не обнаружится нужного блока catch, то вызывается стандартная функция завершения terminate(), которая вызывает функцию abort().
Выход из обработчика по исключению может привести к выходу из функции. Очень важно, что стандарт в этом случае гарантирует вызов деструкторов для уничтожения локальных объектов.
После выполнения операторов блока catch выполняются операторы, расположенные после всей конструкции try...catch. Если во время работы в блоке try не обнаружено исключительной ситуации, то все блоки catch пропускаются и программа продолжает выполнение с первого после всех блоков catch оператора.
Слайд 6 Обработка исключений в C++
Пример 1. Передача в обработчик
catch целого числа
Слайд 7 Обработка исключений в C++
Пример 2: Передача в обработчик
catch символьной строки
Слайд 8 Обработка исключений в C++
Пример 3: Выбрасывание исключения в
функции
Слайд 9 Обработка исключений в C++
Пример 4: Передача в обработчик
catch объекта класса исключения
Слайд 10 Обработка исключений в C++
Пример 4: Передача в обработчик
catch объекта класса исключения
Слайд 11 Обработка исключений в C++
Пример. Параметрами функции На являются три
стороны треугольника, а вычислять нужно высоту, опущенную на сторону, указанную
первой. Если параметры-стороны заданы в порядке а, b, с, то вычислять надо высоту, опущенную на сторону а. Как известно, высота, опущенная на сторону а, вычисляется по формуле:
где р = (а + b + с)/2 — полупериметр треугольника. Квадратный корень представляет собой формулу Герона для вычисления площади треугольника. Таким образом, нам надо проверить, что:
□ ни один из параметров (сторона треугольника) не меньше нуля и не равен нулю;
□ выполняются неравенства треугольника для любых сочетаний сторон.
Если эти условия не выполняются, то функция должна генерировать исключение, которое является сообщением об ошибке с дополнительной информацией об ошибке (указанием длин сторон треугольника, которые вызвали генерацию исключения).
Для описания исключения создается класс исключения, специализированный под задачу. В классе-исключении объявляются поля: стороны треугольника, сообщение об ошибке и определен конструктор с параметрами.
Передавать объект-исключение в обработчик catch будем по константной ссылке.
Слайд 12 Обработка исключений в C++
Классы стандартных исключений
class exception
{//... };
class logic_error : public exception {//... };
class domain_error : public logic_error {//... };
class invalid_argument : public logic_error {//..};
class length_error : public logic_error {//...};
class out_of_range : public logic_error {//...};
class runtime_error : public exception {//... };
class range_error : public runtime_error {//...};
class overflow_error : public runtime_error {//...};
class underflow_error : public runtime_error {//...};
class bad_alloc : public exception {//... };
class bad_cast : public exception {//... };
class bad_tipeid : public exception {//... };
class bad_exception : public exception {//... };
class ios_base::failure : public exception {//... };
Слайд 13 Обработка исключений в C++
В языке C++ в составе стандартной
библиотеки реализован ряд стандартных исключений, которые организованы в иерархию классов
(см. слайд).
Мы можем определять собственные классы исключений, унаследовав их от класса exception.
Все стандартные классы исключений являются наследниками класса exception.
Названия классов logic_error и runtime_error условны. Предполагается, что исключения первого типа сигнализируют об ошибках в логике программы, например о невыполнении некоторого условия. Категория runtime_error — это ошибки, которые возникают в результате непредвиденных обстоятельств при выполнении программы, например переполнение при операциях с дробными числами.
Эти исключения (logic_error и runtime_error) программа должна генерировать сама оператором throw. А вот следующие 5 стандартных исключений генерируют различные механизмы C++.
Исключение bad__alloc генерирует операция new (или new[]), если запрос на память не может быть удовлетворен.
Исключения bad__cast и bad_typeid генерируются механизмом RTTI (Run-Time Type Identification — динамическая идентификация типов).
Исключение ios__base::failure генерируется системой ввода-вывода.
Исключение bad_exception играет важную роль при нарушении функцией спецификации исключения.
Стандартные исключения включают функцию-метод what(), которая выдает строку-сообщение об ошибке.
Слайд 14 Обработка исключений в C++
Пример 5: Использование стандартного класса
исключения
Слайд 15 Обработка исключений в C++
Пример 6: Механизмы обработки исключений.
Создание класса исключения на основе класса std::exeption
Слайд 16 Обработка исключений в C++
Пример 6: Механизмы обработки исключений.
Создание класса исключения на основе класса std::exeption
Слайд 17 Обработка исключений в C++
Пример 6: Механизмы обработки исключений.
Создание класса исключения на основе класса std::exeption
Слайд 18 Обработка исключений в C++
Пример 6: Механизмы обработки исключений.
Создание класса исключения на основе класса std::exeption
Слайд 19 Обработка исключений в Java
Иерархия классов-исключений Java. Типы исключений
в Java.
Слайд 20 Обработка исключений в Java
Объект-исключение в Java – это
объект класса исключения (стандартного или пользовательского).
В Java существует целая
иерархия стандартных классов исключений (см. слайд).
Все исключения в Java имеют общего предка – класс Throwable. Он имеет два важных подкласса - Exception и Error. Исключения (Exceptions) являются результатом возникших внутри программы проблем, которые в принципе решаемы и предсказуемы. Ошибки (Errors) представляют собой более серьёзные проблемы, которые, согласно спецификации Java, не следует пытаться перехватить в приложении, написанном достаточно рационально (например ошибка OutOfMemoryError происходит в тех случаях, когда JVM не хватает памяти для выполнения программы). Кроме того, у класса Exception есть важный потомок - RuntimeException (исключение времени выполнения). Этот класс и его потомки представляют собой исключения, которые возникают во время "нормальной работы Java-машины" (примерами таких исключений являются попытки использования нулевых ссылок на объекты, деления на ноль или выход за границы массива).
В Java все исключения делятся на три типа: контролируемые исключения(checked), ошибки (Errors) и исключения времени выполнения (RuntimeExceptions) - последние два типа также объединяют в категорию неконтролируемых (unchecked) исключений. В чем различие?
Контролируемые исключения обязательны для обработки в коде программы, они должны быть обработаны либо включением в блок try-catch, либо объявлены в сигнатуре метода с помощью ключевого слова throws. Компилятор проверяется наличие обработки для этих исключений, если ее нет, то выдает сообщение об ошибке, поэтому они и называются контролируемые.
Неконтролируемые (unchecked) исключения не требуют обязательной обработки, поскольку представляют собой те ситуации, когда ошибка не зависит непосредственно от программиста (например произошёл сбой в аппаратном обеспечении), либо те, когда ошибку обрабатывать не имеет смысла, т.к. проще внести изменения в код - к ним относятся все потомки классов Error и RuntimeException.
Слайд 21 Обработка исключений в в Java
Таблица1. Методы класса Throwable
Слайд 22 Обработка исключений в Java
Операторы для работы с
исключениями
try { // код, который выбрасывает исключение
[
throw объект_исключения; ]
}
catch(Тип_исключения_1 объект){
// код для обработки исключения
}
catch(Тип_исключения_2 объект){
// код для обработки исключения
}
...
finally { // код, который выполняется обязательно
}
// синтаксис метода, выбрасывающего исключения
тип имя_метода(аргументы) throws класс-исключение1,...
{ // тело метода }
Слайд 23 Обработка исключений в Java
В Java для работы с
исключениями используются операторы try, catch и finally, а также ключевое
слово throws. В блок try помещается программный код, который отслеживается на случай, если возникнет исключительная ситуация. Если исключительная ситуация возникает, то управление передается блоку catch. Программный код в этом блоке выполняется, только если возникает исключительная ситуация, причем не любая, а определенного типа (класса исключения). Аргумент, определяющий, какого типа исключительные ситуации обрабатываются в блоке catch, указывается после ключевого слова catch в круглых скобках.
Поскольку в блоке try могут возникать исключения разных типов, для каждого из них можно предусмотреть свой блок catch. Если блоков catch несколько, при возникновении исключительной ситуации они перебираются последовательно до совпадения типа исключительной ситуации с аргументом блока catch.
После блоков try и catch можно указать блок finally с кодом, который выполняется в любом случае вне зависимости от того, возникла исключительная ситуация или нет.
Может случиться, что в блоке try возникла ошибка, но подходящего блока catch для ее обработки нет. В этом случае исключение выбрасывается из метода и должно быть обработано внешним к методу программным кодом. Согласно правилам языка Java, исключения, которые не обрабатываются в методе и выбрасываются из метода, указываются в сигнатуре метода после ключевого слова throws. То есть указываются классы выбрасываемых из метода исключений.
Если возникает ошибка, обработка которой в программе не предусмотрена, используется обработчик исключительной ситуации по умолчанию, который выводит сообщение об ошибке и программа завершает работу.
Для явного выбрасывания исключения используется оператор throw.
Слайд 24 Обработка исключений в Java
Пример 7. Не явное выбрасывание
исключения
Слайд 25 Обработка исключений в Java
Пример 7. Не явное выбрасывание
исключения
Слайд 26 Обработка исключений в Java
В классе Throwable переопределяется метод
toString(), который, как известно, определен в общем суперклассе Object, причем
переопределяется он так, что в качестве результата возвращает строку, описывающую соответствующую ошибку. Напомним, что метод toString() вызывается автоматически, например, при передаче объекта-исключения методу println() в качестве аргумента. Соответствующий пример программы и результат ее выполнения представлен на слайде.
В первой текстовой строке, выведенной на экран, текст после слова Ошибка: появился в результате преобразования объекта исключения e в текстовый формат с помощью метода toString().
Слайд 27 Обработка исключений в Java
Пример 8. Явное выбрасывание исключения
Слайд 28 Обработка исключений в Java
Пример 8. Явное выбрасывание исключения
Слайд 29 Обработка исключений в Java
Пример 9. Обработка контролируемого исключения
(вариант 1)
Слайд 30 Обработка исключений в Java
Пример 9. Обработка контролируемого исключения
(вариант 2)
Слайд 31 Обработка исключений в Java
Пример 10. Создание и использование
класса исключения
Слайд 32 Обработка исключений в Java
Пример 10. Создание и использование
класса исключения
Слайд 33 Обработка исключений в Java
Создание собственного исключения сводится к
созданию подкласса класса Exception, который, в свою очередь, является подклассом
класса Throwable.
В программе описывается класс пользовательского исключения MyException. У класса есть три поля: min и max типа double и error - объект класса String. Также в классе переопределяется метод toString(), который возвращает строку сообщения об ошибке.
В классе Primer определяется статический метод MyLog() с аргументом типа double. В качестве результата метод возвращает значение типа double. Метод описан как способный выбрасывать исключение пользовательского класса MyException. В теле метода для значения аргумента x вычисляется натуральный логарифм по формуле: ln( x ⋅( x −1)) .
Если аргумент, переданный методу MyLog(), лежит вне пределов диапазона [0, 1], методом возвращается значение Math.log(x*(x-1)) Если же аргумент метода MyLog() попадает в диапазон [0, 1], приведенное выражение вычислено быть не может, поскольку у натурального логарифма аргумент отрицательный. В этом случае методом MyLog() генерируется и выбрасывается исключение пользовательского типа MyException. Аргументами конструктору при этом передаются границы диапазона [0 , 1] и описание ошибки (неверный аргумент).
В главном методе программы выполняется попытка вычислить значение методом MyLog() и вывести его на экран. При этом отслеживается возможность появления исключения класса MyException. В случае если соответствующая ошибка возникает, выполняется ее обработка, которая состоит в том, что на экран выводится описание объекта исключения. Этот объект передается методу println() в блоке catch, а наблюдаемый при этом результат отражает способ переопределения метода toString() в классе MyException.
Слайд 34 Обработка исключений в С#
Операторы для работы с
исключениями
try { // код, который выбрасывает исключение
[
throw объект_исключения; ]
}
catch(Тип_исключения_1 объект){
// код для обработки исключения
}
catch(Тип_исключения_2 объект){
// код для обработки исключения
}
...
// аналог catch(...) C++
catch {
// код для обработки исключения
}
finally { // код, который выполняется обязательно
}
Слайд 35 Обработка исключений в C#
Исключения в С# представлены классами.
Все классы исключений могут быть унаследованы от встроенного класса исключений Exception,
который является частью пространства имен System.
Объект-исключение в C# – это объект класса исключения (стандартного или пользовательского).
В C# существует обширная иерархия стандартных классов исключений.
Все исключения в C# имеют общего предка – класс Exception. Он хранит всю информацию о произошедшем исключении. Эту информацию мы можем получить через свойства класса:
Helplink: хранит адрес интернет-ресурса, на котром можно найти всю информацию об ошибке;
InnerException: объект класса Exception, хранит информацию об исключении, которое послужило причиной текущего исключения;
Message: хранит сообщение об исключении, текст ошибки;
Source: хранит имя объекта или сборки, которое вызвало исключение;
StackTrace: возвращает строковое представление стека вызовов, которые привели к возникновению исключения;
TargetSite: возвращает метод, в котором и было вызвано исключение.
Класс Exception имеет два важных подкласса - ApplicationException и SystemException. Они определяют две общие категории исключений: программные и исключения, образованные средой выполнения (т.е. CLR).
У класса SystemException имеется большое количество подклассов, среди которых можно выделить: ArithmeticException – класс, который представляет арифметические исключения такие как DivideByZeroException (деление на ноль, наследуется из ArithmeticException) или OverflowException (переполнение, наследуется из ArithmeticException) и т.д. На основе класса исключений ApplicationException можно будет сформировать свои пользовательские классы исключений.
Вся обработка исключений в C# строится на 4 операторах: try, catch, throw, finally, которые вы уже знаете из Java и C++. В C# они используются приблизительно также. Приведем ряд примеров, для того чтобы показать принцип их работы.
Слайд 36 Обработка исключений в С#
Пример 11. Не явное выбрасывание
исключения
Слайд 37 Обработка исключений в С#
Пример 11. Не явное выбрасывание
исключения
Слайд 38 Обработка исключений в С#
Пример 12. Явное выбрасывание исключения.
Слайд 39 Обработка исключений в С#
Пример 12. Явное выбрасывание исключения.
Слайд 40 Обработка исключений в С#
Пример 13. Создание собственного класса
исключения.
Слайд 41 Обработка исключений в С#
Пример 13. Создание собственного класса
исключения.
Слайд 42 Обработка исключений в C#
В примере 12 в классе
Person при установке возраста происходит проверка, и если возраст меньше
18, то выбрасывается исключение. Класс Exception принимает в конструкторе в качестве параметра строку, которая затем передается в его свойство Message.
Иногда удобнее использовать свои классы исключений. В примере 13 создается класс PersonException, который кроме пустого конструктора ничего не имеет, и то в конструкторе мы просто обращаемся к конструктору базового класса Exception, передавая в него строку message.
Если в методе Console.WriteLine указать объект класса исключения, то автоматически будет вызван метод toString() класса Exception, который возвращает сообщение об исключении, текст ошибки и строковое представление стека вызовов, которые привели к возникновению исключения.
Преимущества, которые дает нам использование исключений
Разделение обычного кода и кода обработки ошибок
Возможность передачи исключений для обработки вверх по стеку вызовов
Группировка и обработка ошибок по типам
Слайд 43Контрольные вопросы
Понятие исключения. Как организуется обработка исключений в С++. Примеры.
Как
организуется обработка исключений в Java. Примеры.
Как организуется обработка исключений в
С#. Примеры.