Блок-функция-try
Устанавливает обработчик исключений вокруг тела функции.
Синтаксис
Блок-функция-try — одна из альтернативных форм синтаксиса тело-функции, которая является частью определения функции.
try инициализатор-конструктора (необязательно) составное-выражение последовательность-обработчиков |
| инициализатор-конструктора | - | список инициализации членов, разрешен только в конструкторах |
| составное-выражение | - | заключённая в фигурные скобки последовательность выражений, которая составляет тело функции |
| последовательность-обработчиков | - | последовательность одного или нескольких блоков catch |
Объяснение
Блок-функция-try связывает последовательность блоков catch со всем телом функции и со списком инициализации членов (если используется в конструкторе). Любое исключение, брошенное из любого оператора в теле функции или (для конструкторов) из любого конструктора члена или базового конструктора или (для деструкторов) из любого деструктора члена или базового деструктора, передаёт управление в последовательность-обработчиков так же, как исключение, брошенное в обычном блоке try.
#include <iostream>
#include <string>
struct S
{
std::string m;
S(const std::string& str, int idx)
try : m(str, idx)
{
std::cout << "S(" << str << ", " << idx << ") constructed, m = " << m << '\n';
}
catch(const std::exception& e)
{
std::cout << "S(" << str << ", " << idx << ") failed: " << e.what() << '\n';
} // implicit "throw;" here for constructor
};
int main()
{
S s1{"ABC", 1}; // does not throw (index is in bounds)
try
{
S s2{"ABC", 4}; // throws (out of bounds)
}
catch (std::exception& e)
{
std::cout << "S s2... raised an exception: " << e.what() << '\n';
}
}Перед входом в любые блоки catch блока-функции-try для конструктора все полностью сконструированные члены и базы уже были уничтожены.
|
Если блок-функция-try находится в делегирующем конструкторе, который вызвал не-делегирующий конструктор, который завершился успешно, но затем тело делегирующего конструктора выбрасывает исключение, то деструктор этого объекта будет завершен до входа в любые блоки catch блока-функции-try. |
(с C++11) |
Перед входом в любые блоки catch блока-функции-try для деструктора все базы и не-вариативные члены уже были уничтожены.
Поведение не определено, если блок catch блока-функции-try, используемый в конструкторе или деструкторе, обращается к базе или нестатическому члену объекта.
Каждый блок catch в блоке-функции-try для конструктора должен завершиться сбросом исключения. Если управление достигает конца такого обработчика, текущее исключение автоматически повторно выбрасывается, как если бы это было сделано посредством throw;. Оператор return не разрешён в любом блоке catch блока-функции-try конструктора.
Достижение конца блока catch блока-функции-try для деструктора также автоматически повторно выбрасывает текущее исключение, как если бы это было сделано посредством throw;, но оператор return разрешён.
Для всех других функций достижение конца блока catch равносильно return; если тип возврата функции является (возможно, квалифицированным cv) void, в противном случае поведение не определено.
Примечания
Основная цель блоков-функций-try — реагировать на исключение, брошенное из списка инициализации членов в конструкторе, ведя журнал, повторно выбрасывая, изменяя объект исключения и повторно выбрасывая, выбрасывая другое исключение или завершая программу. Они редко используются с деструкторами или с обычными функциями.
Блок-функция-try не перехватывает исключения, брошенные копирующими/перемещающими конструкторами и деструкторами параметров функции, переданных по значению: эти исключения выбрасываются в контексте вызывающей функции.
| Блок-функция-try функции верхнего уровня потока не перехватывает исключения, брошенные конструкторами и деструкторами объектов с локальным временем жизни потока (за исключением конструкторов локальных объектов потока). | (с C++11) |
Аналогично, блок-функция-try функции main() не перехватывает исключения, брошенные конструкторами и деструкторами статических объектов (за исключением конструкторов локальных статических объектов).
Область видимости и время жизни параметров функции (но не любых объектов, объявленных в самой функции), распространяется до конца последовательности-обработчиков.
int f(int n = 2) try
{
++n; // increments the function parameter
throw n;
}
catch(...)
{
++n; // n is in scope and still refers to the function parameter
assert(n == 4);
return n;
}Отчёты об ошибках
Следующие отчёты об ошибках, меняющие поведение, были применены ретроактивно к ранее опубликованным стандартам C++.
| DR | Применено к | Поведение как опубликовано | Правильное поведение |
|---|---|---|---|
| CWG 1167 | C++98 | не было указано, будет ли блок-функция-try для деструктора перехватывать исключения из деструктора базы или члена | такие исключения перехватываются |
© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/w/cpp/language/function-try-block