【发布时间】:2017-05-22 05:50:28
【问题描述】:
“Effective Modern C++”的第 14 项建议在函数不发出异常时声明函数 noexcept。我有一个类有许多小成员函数,这些函数由于非常琐碎的原因而不能抛出,例如他们只对 POD 执行简单的数学运算。我应该声明这样的函数noexcept吗?当甚至编译器可以肯定地检测到没有抛出的可能性时,这对我来说似乎有点矫枉过正。
编辑:为了稍微澄清我的问题,this 问题中给出的建议是“在函数显然永远不会抛出时使用它”。但是,如果很明显(即使对于编译器)该函数永远不会抛出,为什么要使用 noexcept 呢?请注意,我必须将程序的绝大多数函数标记为noexcept,只有在给出令人信服的理由时我才会这样做。
【问题讨论】:
-
@JesperJuhl 我之前看到过这个问题,但没有发现它有帮助,因为建议简化为“只要函数明显不会抛出就使用它”而没有提供任何理由。如果很明显该函数不会抛出,为什么还要添加
noexcept? -
因为它对编译器来说可能并不明显,而且它还为您的 API 用户提供了额外的文档。
-
@JesperJuhl 我编辑了我的问题以使其更清楚,但编译器应该很明显,所讨论的函数不能抛出,因为它们仅包含分支、简单算术、循环等。没有内存分配或任何可能会抛出的东西。
-
@AlessandroPower:你掉进了一个陷阱,根据它看起来的英文单词来解释关键字,而不是它的实际定义。
nothrow并不是说“这个函数中的代码都不能抛出”,而是说“这个函数不会有异常逃逸”。区别体现在两种方式——如果函数捕获异常,则完全允许有抛出的代码。并且可能会转义不是本质上抛出的异常(来自函数自己的代码),而是来自从该函数调用的函数。 -
一般来说,对于编译器来说,推断一个函数是否本质上泄漏异常很容易,但是外部异常,尤其是在存在多态性或间接性的情况下,需要注释(
nothrow关键字)。