我有一个带有自定义异常的模板类:
MyClass<T>::MyException;
使用我的类时,我只关心是否抛出了异常,因此我可以通过编程方式处理它。因此,当我发现异常时,我不愿意为此命名。
try {
MyClass<T>::MyMethod ();
} catch (typename MyClass<T>::MyException) {
//Act appropriately
}
我想知道添加引用运算符时是否有任何区别,例如
} catch (typename MyClass::MyException &) {
在任何一种情况下,除了识别类型之外,我最终不会使用捕获的异常。一个与另一个有任何权衡或性能影响吗?
答案 0 :(得分:6)
按值捕获会创建异常对象的副本,无论您是否使用它。所以不要。始终以引用方式捕获。没有理由抓住价值。
另外,typename
关键字是多余的,因为没有涉及任何模板。
答案 1 :(得分:1)
在第一种情况下:
catch (typename MyClass:MyException)
捕获时将调用复制构造函数。此外,如果您从MyException
派生了另一个异常,它将被切片。
当你这样做时:
catch (typename MyClass:MyException &)
您不会导致复制(因此效率更高),您可以安全地捕获派生的异常。
答案 2 :(得分:0)
您应始终通过引用捕获异常。这只是一个好习惯。
但是,在这种特殊情况下,我认为不重要。没有切片问题,因为您没有命名捕获的异常对象,因此您可能无法访问任何成员。异常是否被复制两次并不重要 - 它只是一个异常的情况,并且复制很便宜(如果抛出是正常程序流程的一部分,那么无论如何你都有更大的问题。)
重点是:按价值追赶也不会给你买任何东西。在源代码中保存一个字符不算数:)恰恰相反,它在将来会产生错误的可能来源。