Нам действительно нужны std::error_category и std::error_condition?

Итак, на моем пути к пониманию того, как работает std::error_code, я начинаю задаваться вопросом, действительно ли нам нужны std::error_condition и std::error_category. Я пытаюсь реализовать то, что находится в этом и этого руководства, и объем работы нетривиален. наряду с тем, что он довольно хрупкий (в настоящее время я застрял, пытаясь понять, почему этот код вызывает ошибки связывания с повторяющимися символами.

Не проще ли создать подкласс std::error_code, добавить свойство и метод message, а затем позволить std::error_code быть сопоставимым с перечислением, в котором определены коды ошибок? Я изо всех сил пытаюсь понять, зачем мне вообще нужны std::error_category и std::error_condition.


person ruipacheco    schedule 24.08.2017    source источник
comment
Существует несколько способов обработки ошибок в C++, единственного правильного способа не существует. Если он вам не нужен, не используйте его.   -  person Rinat Veliakhmedov    schedule 24.08.2017


Ответы (1)


Основное преимущество заключается в том, что error_code является копируемым типом, который можно передавать из библиотеки в библиотеку без необходимости использования какого-либо динамического распределения памяти или шаблонов, что делает его очень легким и простым в работе.

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

Однако все меняется при написании библиотеки, предназначенной для использования другими людьми (например, ASIO, поскольку вы связались с think-async.com). У вас может быть библиотека, получающая экземпляр error_code, и она сможет передавать его чисто и эффективно, не зная ничего о коде, использующем библиотеку, или не создавая шаблоны для каждой функции обработки ошибок. тип.

В этом контексте категории ошибок важны при работе с несколькими источниками ошибок, поскольку данный код ошибки может означать две разные вещи в зависимости от источника ошибки.

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

person Frank    schedule 24.08.2017
comment
Я бы добавил, что это также упрощает перенос пользовательских кодов ошибок через стандартные типы исключений, такие как std::system_error. Клиентскому коду, который использует вашу библиотеку, не нужно ничего знать о вашей пользовательской категории ошибок. Они могли бы просто поймать std::system_error и, вызвав общие методы std::error_code, записать их в файл журнала, где значение ошибки, название категории ошибок, которую вы определили, и строковое сообщение, которое вы определили в появится ваша категория ошибок. Гораздо лучше, чем просто выводить код ошибки 123, когда никто не знает, к какому контексту он относится. - person zett42; 24.08.2017