Пусто throw
спецификации полезны, поскольку они фактически позволяют оптимизировать компилятор на сайте вызывающей стороны, как знает Википедия (у меня нет под рукой технической цитаты).
И по причинам возможностей оптимизации nothrow-спецификации не устарели в следующем стандарте, они просто больше не похожи на throw ()
, а называются noexcept
. Ну да, и они работают немного по-другому.
Здесь - обсуждение noexcept
, в котором также подробно объясняется, почему традиционные спецификации nothrow-prohobit оптимизируются на сайте вызываемого абонента.
Как правило, вы платите за каждую имеющуюся у вас throw
спецификацию, по крайней мере, с помощью полностью совместимого компилятора, который, по-видимому, не всегда был у GCC. Эти throw
спецификации должны быть проверены во время выполнения, даже пустые. Это происходит потому, что если возникает исключение, которое не соответствует спецификации throw
, разматывание стека должно происходить в пределах этого стекового фрейма (так что вам нужен код для этого в дополнение к проверке соответствия) и затем std::unexpected
должен называться. С другой стороны, вы потенциально экономите время / пространство для каждой пустой throw
спецификации, поскольку компилятор может делать больше предположений при вызове этой функции. Я выдохну, сказав, что только профилировщик может дать вам окончательный ответ о том, страдает или улучшается ваш конкретный код с помощью ( пусто !) throws
спецификации.
В качестве обходного пути к вашей реальной проблеме может ли работать следующее?
- Введите
#define NOTHROW throw ()
и используйте его для what
вашего исключения и других вещей.
- Когда GCC реализует
noexcept
, переопределите NOTHROW
.
Обновление
Как отмечает @James McNellis, throw ()
будет совместимым с прямой пересылкой. В этом случае я предлагаю просто использовать throw ()
там, где вам нужно, и, кроме этого, если есть сомнения, профиль.