2014-11-18 3 views
4

Предположат, есть следующий код:Взаимосвязь между повышающим :: исключением и стандом :: исключением

try { 
     // Do some boost stuff here 
} 
catch (const std::exception & stdEx) { 
    cout << stdEx.what() << endl; 
} 

Вопросов:

1) Я знаю, что код работает для некоторых исключений наддува, хотя станд: : exception и boost :: exception не относятся к одному пути наследования. Почему это работает?

2) Работает ли это так для всех исключений форсирования? Другими словами, существуют ли примеры, когда обработчик boost :: exception, который находится ниже обработчика std :: exception, может быть запущен?

+0

Не вдаваясь в код Boost, я подозреваю, что он имеет условные обозначения, которые откладываются до версий 'std' при запуске на соответствующем компиляторе, поэтому они фактически * являются * в одном пути наследования. –

ответ

6

Как вы сказали, boost::exception не происходит от std::exception. По той причине, проверьте соответствующий FAQ:

Несмотря на то что виртуальное наследование должно быть использовано при выводе из базовых типов исключений, довольно часто типов исключений (в том числе тех, которые определены в стандартной библиотеке) не получают от std::exception практически ,

Если boost::exception происходит от std::exception, используя enable_error_info функции с такими определяемым пользователем типами бы ввести опасную двусмысленность, которая сломает все catch(std::exception &) заявления.

Конечно, boost::exception не должен использоваться для замены std::exception в качестве базового типа в иерархиях типов исключений. Вместо этого, он должен быть включен в качестве виртуальной базы, в дополнение к std::exception (который должен также, вероятно, быть получен практически.)

recommendation, чтобы иметь специфические наддува классы исключений происходят (практически) с обеих boost::exception и std::exception, и не только от boost::exception.

Исключения некоторых дополнительных библиотек получены только от std::exception (например, boost::bad_lexical_cast), некоторые из них (например, boost::xpressive::regex_error). Я не знаю, что происходит только от boost::exception, хотя, я бы сказал, что поймать только std::exception должен поймать всех.

+0

Как вы объясните, что boost :: bad_lexical_cast может быть захвачен (boost :: exception &), если первый не является производным от boost :: exception? – James

+0

@James: потому что ['boost :: throw_exception'] (http://www.boost.org/doc/libs/1_57_0/libs/exception/doc/throw_exception.html) был использован для исключения исключения, которое обогащает исключение - среди прочего, путем динамического добавления 'boost :: exception' в качестве базы (для получения более подробной информации щелкните ссылку). –

Смежные вопросы