C++重载函数的异常规范

4
class ESClass
{
public:
    void PrintMe() throw();
    void PrintMe(int) throw(int);
};

我想知道我们是否可以为重载函数定义不同的异常规范。换句话说,我们是否可以给PrintMe函数的不同版本赋予不同的异常规范?

来自VS2010的注意事项:

警告C4290:忽略C++异常规范,除非表示函数不是__declspec(nothrow)


1
Visual Studio的警告已经存在很久了。这不是它唯一会警告你不符合C++标准的情况。 - André Caron
1
我认为Fred希望你阅读到它所说的那个点:“因此,根据我们作为社区迄今为止学到的最佳建议:道德准则1:永远不要编写异常规范。 道德准则2:可能除了空规范外,但如果我是你,我甚至会避免使用它。” - André Caron
1
@q0987 - 这不是关于函数重载的问题,而是关于在VC++中使用异常规范。编译器只处理throw(),而不处理其他任何内容。 - Bo Persson
@André Caron:没错,这就是为什么我在评论中加入了那句引用。8v) - Fred Larson
1
@Fred:当我发表评论时,你的评论不在其中 :-) - André Caron
显示剩余3条评论
1个回答

9
是的:它们是不同的函数,它们可以有不同的异常规范。
如果一个虚成员函数有异常规范,任何{{override}}(而不是{{overload}})必须具有至少与被覆盖的成员函数一样严格的异常规范。
当然,在那些必须的几种情况下之外,你应该永远不要编写异常规范
Visual C++不完全支持异常规范,因此它允许一些实际上不符合C++语言规范的代码。你提到的警告只是意味着你正在使用使用了Visual C++不支持的C++语言特性的代码:

一个函数使用异常规范进行声明,Visual C++接受但不实现。在编译期间忽略异常规范的代码可能需要重新编译和链接,以便在未来支持异常规范的版本中重用。


虽然这是合法的,但从不同的重载中抛出不同的异常集是一个不好的习惯。当仅更改传递给函数的参数时,很容易忘记更新catch子句... - André Caron
关于异常规范,"strictness" 的含义是什么? - pmr
@JamesMcNellis,即使在VC ++ 18.00.31101中仍会发出C4290警告。您打算在前端修复它吗? - Anton K
1
@AntonK:如果你在询问我们是否计划实现对动态异常规范的全面支持,那我认为答案是“可能不会”。动态异常规范在C++11中已经被弃用。 - James McNellis
@JamesMcNellis,感谢您的澄清。很抱歉,我在标准中错过了这一点。 - Anton K
显示剩余3条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接