如果您通过使用程序的 ABT 来避免指向函数的指针(并认为它们不安全),这当然是可能的。Clang 的 AST 是(尽管它的名字)这样的 ABT:您将看到函数的声明和定义。通过一次做一个定义,你已经有了一个很好的基线。
另一方面,我想知道这是否实用。看,问题是任何执行内存分配的函数都(自愿地)标记为可能抛出(因为new
从不返回 null,而是抛出bad_alloc
)。因此,noexcept
在大多数情况下,您将仅限于少数功能。
当然还有像@GManNickG 这样的所有动态条件暴露,例如:
void foo(boost::optional<T> const t&) {
if (not t) { return; }
t->bar();
}
即使T::bar
is noexcept
,取消引用 anoptional<T>
可能会抛出(如果什么都没有)。当然,这忽略了我们已经排除了这个事实(这里)。
如果没有明确的条件说明函数何时可能throw
,static
分析可能会被证明是……无用的。语言习语的设计考虑到了例外情况。
注意:作为题外话,可以重写可选类,以免暴露解引用,因此noexcept
(如果回调是):
template <typename T>
class maybe {
public:
template <typename OnNone, typename OnJust>
void act(OnNone&& n, OnJust&& j) noexcept(noexcept(n()) and
noexcept(j(std::declval<T&>())))
{
if (not _assigned) { n(); return; }
j(*reinterpret_cast<T*>(&_storage));
}
private:
std::aligned_storage<sizeof(T), alignof(T)>::type _storage;
bool _assigned;
};
// No idea if this way of expressing the noexcept dependency is actually correct.