C++学习笔记——异常处理

来源:互联网 发布:防火墙端口转换 编辑:程序博客网 时间:2024/06/05 09:52

异常处理

1. 异常处理的思想与程序实现

image1

  • 异常处理并不一定在异常发生的位置处理,而是向上级抛出,异常沿函数调用栈传到异常处理模块后将其处理

异常处理的语法:

抛出异常的程序段:

……

throw 表达式;

……

捕获并处理异常的程序段

try

​ 复合语句

catch (异常声明)

​ 复合语句

catch (异常声明)

​ 复合语句

……

  • 若有异常则通过throw创建一个异常对象并抛掷
  • 将可能抛出异常的程序段嵌在try块中,通过正常的顺序执行到try语句,然后执行块内的保护段
  • 如果保护段执行期间没有引起异常,则catch子句不执行
  • catch子句的通过其在try块后出现的顺序被检查
  • 如果匹配的处理器未找到,则库函数terminate被自动调用,默认功能是终止程序
int divide(int x, int y){  if (y == 0)    // 将被除数作为异常对象抛出    throw x;  return x / y;}int main(){  try{    cout << "5/2 = " << divide(5,2) << endl;    // 抛出异常后之后的语句不再执行    cout << "8/0 = " << divide(8,0) << endl;    cout << "7/1 = " << divide(7,1) << endl;  }catch(int e){    cout << e << "is divided by zero!" << endl;  }  cout << "That is OK." << endl;  return 0;}
  • 异常接口声明:一个函数显示声明可能抛出的异常,有利于函数调用者为异常处理做好准备
void fun() throw(A, B, C, D);
  • 若无异常接口声明,则此函数可以 抛掷任何类型的异常
  • 不抛掷任何类型异常的函数声明如下:
void fun() throw();

2. 异常处理中的构造与析构

自动的析构:找到一个匹配的catch异常处理后,将初始化异常参数,将对应的try块开始到异常被抛掷处之间构造(尚未析构)的所有对象自动进行析构,从最后一个catch处理之后开始恢复执行

3. 标准程序库异常处理

image2

标准异常类的基础:

  • exception:标准程序库异常类的公共 基类
  • logic_error:表示可以在程序中被预先检测到异常,这类异常可以被避免
  • runtime_error:表示难以被预先预测的异常

Image3

#include <iostream>#include <cmath>#include <stdexcept>using namespace std;double area(double a, double b, double c) throw (invalid_argument){  // 三边是否为正  if (a <= 0 || b <= 0 || c <= 0)    throw invalid_argument("the side length should be positive");  // 是否满足三角不等式  if (a + b <= c || b + c <= a || c + a <= b)    throw invalid_argument("the side length should fit the triangle inequation");  double s = (a + b + c) / 2;  return sqrt(s * (s-a) * (s-b) * (s-c));}int main(){  double a, b, c;  cout << "Please input the side lengths of a triangle:";  cin >> a >> b >> c;  try {    double s = area(a,b,c);    cout << "Area:" << s << endl;  }catch(exception & e){    cout << "Error:" << e.what() << endl;  }  return 0;}