Вопросы относительно упорядочивания операторов выгоды в блоке выгоды - конкретный компилятор или стандарт языка?

Я в настоящее время использую Visual Studio Express C++ 2008 и имею некоторые вопросы об упорядочивании блока выгоды. К сожалению, я не мог найти ответ в Интернете, таким образом, я ставлю эти вопросы экспертам.

Я замечаю, что, если выгода (...) не помещается в конце блока выгоды, компиляция приведет к сбою с ошибкой C2311. Например, следующее скомпилировало бы:

catch (MyException)
{
}
catch (...)
{
}

в то время как следующее не было бы:

catch (...)
{
}
catch (MyException)
{
}

a. Я мог спросить, определяется ли это в стандарте языка C++, или если это - просто компилятор Microsoft, являющийся строгим?

b. C# и Java имеют те же правила также?

c. Как в стороне, я также попытался делать базовый класс и производный класс, и поместить оператор выгоды для базового класса перед оператором выгоды для производного класса. Это скомпилировало без проблем. Там никакие стандарты языка не принимают меры против такой практики?

5
задан Andy 8 March 2010 в 22:00
поделиться

3 ответа

По стандарту порядок имеет значение. По сути, будет пойман первый улов, соответствующий исключению.

a) Поскольку catch (...) сделает любые последующие уловы неактуальными, стандарт разрешает только последний улов.

б) C # и Java имеют похожие правила.

c) перехват (по ссылке или указателю) базы до того, как производный класс сделает код производного неактуальным. Однако стандарт разрешает это

5
ответ дан 13 December 2019 в 19:25
поделиться

Так называемый обработчик по умолчанию catch(...) должен быть последним в списке обработчиков. Это действительно требуется стандартом. Однако это требование относится только к обработчику по умолчанию.

В остальном стандарт не ограничивает упорядочивание обработчиков, что означает, что в общем случае вы можете создать обработчик, который будет "перехватывать" все исключения, которые в противном случае попали бы к другому обработчику ниже по списку (таким образом делая последний обработчик бесполезным).

Более того, совершенно законно повторять одно и то же catch предложение (с одним и тем же типом) несколько раз

catch (int) {
  // ...
}
catch (int) {
  // ...
}

даже несмотря на то, что только первый из них будет иметь шанс поймать хоть что-нибудь. Хороший компилятор выдаст предупреждение для подобных случаев, но формально это не является ошибкой.

3
ответ дан 13 December 2019 в 19:25
поделиться

Из стандарта C++ 15.3/5 "Обработка исключения":

Обработчики для пробного блока искомы в порядке появления. Это позволяет писать обработчики, которые никогда не могут быть выполнены, например, помещая обработчик для производного класса после обработчика для соответствующего базового класса.

A ... в функции объявления исключений обработчика аналогичны функциям ... в объявлении параметров функции; он задает соответствие для любого исключения. Если присутствует, то ... Обработчик является последним обработчиком для своего пробного блока.

3
ответ дан 13 December 2019 в 19:25
поделиться
Другие вопросы по тегам:

Похожие вопросы: