函数如何通知用户它基于函数原型抛出异常?
How do functions inform user that it throws exception based on function prototype?
我经历了几次讨论、教程等,我有一种感觉,没有办法通知用户使用原型,他的函数可能会抛出异常。
例如:
/* AudioStream.h */
class AudioStream
{
int open(struct stream_settings &settings);
}
/* AudioStream.cpp */
int AudioStream::open(struct stream_settings &settings)
{
int err;
err = snd_pcm_open(...);
if (err < 0)
{
/* Throw some exception here */
}
}
如果最终产品最终出现在带有标题的库中。如何确定 open 函数会抛出异常,并且有必要将其放入 try/catch 块中?
谢谢你所有伟大的答案。
与某些在函数签名中指示它"抛出"的语言不同,C++没有这样的机制。这是您必须在函数定义附近的文档或注释中建立的内容。
如前所述,您不一定确定函数是否可以抛出。然而,相反的情况确实是可能的。通过声明函数noexcept
可以保证此函数永远不会引发离开自己的函数体的异常。但是,如果noexcept
函数无论如何都要抛出而不处理异常本身,则程序将被终止。因此,只要函数未声明noexcept
,并且您没有关于该函数的文档或知识,预计它可能会引发异常。
另一种可能性是使用错误代码或std::optional
而不是抛出异常。
我的男人赫伯·萨特(Herb Sutter(也有一个关于例外的精彩演讲。
这里有一些示例,您可以避免异常以支持某种错误代码。
您可以使用noexcept(false)
来显式指定函数可以抛出的内容。这不会为编译器添加任何信息,因为can throw是每个没有noexcept
规范的函数的隐式默认值。
因此,推荐的方法可能是为每个无法抛出的函数添加一个noexcept
说明符。
另请参阅 https://en.cppreference.com/w/cpp/language/noexcept_spec 和添加"noexcept(false("是否以任何方式使代码受益?
C++throw
规范自 11 C++以来已弃用,可以像这样使用:
void f() throw(int);
但是函数原型中没有这个说明符并不能保证函数不会抛出
从 C++ 11 开始,没有除了说明符:
void f() noexcept; // the function f() does not throw
void (*fp)() noexcept(false); // fp points to a function that may throw
但又一次
noexcept 函数的规范不是编译时检查;它只是程序员通知编译器函数是否应该抛出异常的方法
上面的代码示例取自链接页面,您可以在此处阅读有关这些说明符的更多信息。
更新:根据@FrançoisAndrieux建议,我想补充一点,虽然它不是编译时检查,但您可以在编译时检查函数是否具有此说明符,这可能有助于您优化代码
- c++r值引用应用于函数指针
- 如何使用模板函数的函数签名进行SFINAE
- C++从另一个函数退出函数
- 将"函数作为"函数"的"这个"参数传递丢弃限定符 [-允许]
- 保证复制 elis 是否适用于函数参数?
- 代码具有特定于函数的变量,用于更改范围之外的值
- 用于将参数应用于函数的模板函数
- SWIG 多参数类型映射适用于函数,但如果有多个构造函数,则不适用于构造函数
- C++:将参数应用于函数范围
- std::move 如何应用于函数返回值
- 我可以告诉 nvcc 将 #pragma 展开应用于函数中的所有循环吗?
- 此代码是否依赖于函数调用顺序未定义的行为
- C++将标准库算法应用于函数
- 警告 C4180:应用于函数类型的限定符没有意义;忽视
- C++:使用动态内存分配编写类似于 C realloc() 函数的函数(即更改其大小)
- 如何以类似于C函数的方式将dlsym映射到非静态C++成员函数
- 将增量运算符应用于函数
- 模板重载和 SFINAE 仅适用于函数而不是类
- lambda对象相对于函数指针转换的生命周期
- 将using语句应用于函数的返回类型,而不应用于整个命名空间