即使是被C++ 11抛弃的东西,但还是有必要了解一下。当然,抛弃了异常规范throw()之后,C++ 11引入了一种特殊的异常规范——noexcept。
1.什么是异常规范?
C++语法,在函数名后面加上throw(something),表示对函数异常安全作出限制,有如下3种规范:
- void fun () throw ( ):函数不会引发异常。 但是,如果从标记为 throw() 函数引发异常,编译器一般不会调用意外处理函数。因此,如果函数引发异常,则程序可能无法正确执行。
- void fun() throw(…):函数可以抛出任何形式的异常。
- void fun() throw(type):函数可以引发type类型的异常。
然而,针对函数不会引发异常throw(),C++11引入了另一个关键字noexcept指出函数不会引发异常:
void fun() noexcept;
但是,对于上述这种异常规范,也存在一些争议。
2.try、throw和catch语句
若要在 C++ 中实现异常处理,你可以使用 try
、throw
和 catch
表达式。首先,使用 try
块将可能引发异常的一个或多个语句封闭起来。throw
表达式发出信号,异常条件(通常是错误)已在 try
块中发生。
你可以使用任何类型的对象作为 throw
表达式的操作数。 该对象一般用于传达有关错误的信息。 在大多数情况下,我们建议你使用 std:: exception 类或标准库中定义的派生类之一。 如果其中的类不合适,建议你从 std::exception
派生自己的异常类。
(1)try语句块示例
示例1
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
while(cin >> item1 >> tiem2){ try{ //首先检查两条数据是否是关于同一种书籍的 if (item1.isbn() != item2.isbn()) throw runtime_error("Data must refer to same ISBN"); //如果程序执行到了这里,表示两个ISBN是相同的 cout << item1 + item2 << endl; }catch (runtime_error err){ //提醒用户两个ISBN必须一致,询问是否重新输入 cout << err.what() << "\nTry Again? Enter y or n " << endl; char c; cin >> c; if (!cin || c =='n') break; //跳出while循环 } } |
如果抛出异常,输出:
1 2 |
Data must refer to same ISBN Try Again? Enter y or n |
示例2
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
// exceptions #include <iostream> using namespace std; int main () { try { throw 20; } catch (int e) { cout << "An exception occurred. Exception Nr. " << e << '\n'; } return 0; } |
(2)异常规范和try语句块的使用(参考自MSDN异常规范示例):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 |
// exception_specification.cpp // compile with: /EHs #include <stdio.h> void handler() { printf_s("in handler\n"); } void f1(void) throw(int) { printf_s("About to throw 1\n"); if (1) throw 1; } void f5(void) throw() { try { f1(); } catch(...) { handler(); } } // invalid, doesn't handle the int exception thrown from f1() // void f3(void) throw() { // f1(); // } void __declspec(nothrow) f2(void) { try { f1(); } catch(int) { handler(); } } // only valid if compiled without /EHc // /EHc means assume extern "C" functions don't throw exceptions extern "C" void f4(void); void f4(void) { f1(); } int main() { f2(); try { f4(); } catch(...) { printf_s("Caught exception from f4\n"); } f5(); } |
输出结果:
1 2 3 4 5 6 |
About to throw 1 in handler About to throw 1 Caught exception from f4 About to throw 1 in handler |
参考:
MSDN
C++ Primer 5th
cppreference