c++异常处理

来源:互联网 发布:node服务怎么设置域名 编辑:程序博客网 时间:2024/05/22 04:30

异常,通常是指程序困难检测到的,运行是不正常的情况,例如被0除,数组越界访问等等。
异常处理的语法通常是
try
{
   throw()
}

 

catch()
{
}
关键字try以及它后的大括号中的内容我们称其为try块。简单的说,它包含的是可能会出错的地方(就是我们要检测的地方)。当我们检测到一个错误信息的时候,关键字throw就把这个错误抛出来(强呀:)),抛出来怎么办呢?抛哪去呢?我们的catch关键字就给我们解决掉了这个问题。catch通常用来接收throw抛出来的异常。请注意了,throw抛出来的类型要与catch接受的类型要匹配。就像把一个数字5只能附给一个int型的a一样(当然 int型的b也可以...耳后生风,似乎有砖飞来。。。)
下来,让我来学习一下异常处理的三种用法:

 

1:常见的异常处理
我们来看下下一段的代码:
#i nclude <iostream>
#i nclude <string>
#i nclude <math.h>
using namespace std;
class triangle   //定义一个三角形的类
{
public :
float a,b,c,d;   //三角形三边a,b,c,海伦公式常量d
float s;           //三角形面积
public:
triangle()
{}
triangle(float a1,float b1,float c1)
{
   a=a1;
   b=b1;
   c=c1;
}
void judgment()//判断是否是三角形
{
   string yorn;
   if((a+b)<c ||(a+c)<b || (c+b)<a)//任意两边和小于第三边,就不是三角形
   {
     yorn="不是三角形";
     throw(yorn);  
   }         /*如果任意两边和小于第三边,我们就认为是一个异常(不是三角形,让我算什么呢??),用throw抛出。注意,我们定义了一个string形的变量 yorn(是或不是),并将其抛出。接受的时候也要用string类型来接收。下面就会看到~~*/
  
}
void dimension()//计算面积
{
   d=(a+b+c)/2;         //海伦公式
   s=sqrt(d*(d-a)*(d-b)*(d-c));
}
};
void main()
{
triangle a(7,2,3);
try
{
a.judgment();
a.dimension();
     cout<<"三角形a的面积为: "<<a.s<<endl;
}
catch (string &err)   //接受了,接受了,请注意,我还是定义了一个 string形的来接受的。那么我能不能定义一个int   或别的类型的呢?可以,完全可以,只是接受不到罢了:)...又有砖飞来。。。*/
{
cout<<err<<endl;
}
}

 

当然,c++也给提供了一个万能的接收器,
你也可以写成这样
catch(...)
{
cout<<"错了伙计,你知道什么是三角形吗?"<<endl;
}
这里的catch(...)就是一个万能的接收器(别问我为什么,c++规定就是这样写的,就像你不要问我为什么要写这篇文章一样,夜深了,我还在写着...写着...对不起,跑远了,拉回来.)

 

万能接收器也可以和我写的这个catch放一起用,比如你又可以写成:
try
{
a.judgment();
a.dimension();
     cout<<"三角形a的面积为: "<<a.s<<endl;
}

 


catch (string &err)
{
cout<<err<<endl;
}
catch(...)
{
cout<<"错了伙计,你知道什么是三角形吗?"<<endl;
}

 

万能接收器要写在最后面。所有catch的最后一个,要么是你定义的catch () (没有万能的),要么是万能的catch(...)
如果你非要写在别的地方,那么。。重写编译器吧。

 

2:异常规范
当我看着在类中成员函数 void judgment()
{
   string yorn;
   if((a+b)<c ||(a+c)<b || (c+b)<a)
   {
     yorn="不是三角形";
     throw(yorn);
   }
}
时,我的心情澎湃,不能平静。会写抛出了,会写了,我要写两个,删一个留一个。。。等,两个throw,是的我还可以写200个throw,但是我要抛出什么类型呢?目前看来我只想抛出string类型的东西,万一我手快抛错了怎么办(没办法,菜鸟呀,菜鸟总有出错的时候!)。ok,查下资料,喝口小水,看看有没有解决的办法...(翻书中...)

 

工夫不负我有心人呀,翻出了异常规范这个语法。让我看看是怎么实现的
还是上诉的成员函数,改写成
void judgment() throw(string)
{
   string yorn;
   if((a+b)<c ||(a+c)<b || (c+b)<a)
   {
     yorn="不是三角形";
     throw(yorn);
   }
}
这样,就可以保证我只能抛出string类型的异常。

 

在函数的参数列表和函数体之间,throw()语句就是一个异常规范。
编译器保证不能抛出在throw()中包含的类型之外的异常。
比如,我们只想在函数中抛出的异常为int,string类型
我们就可以这样写我们的函数
viod myfun(int a,string b) throw(int ,string)
{
//函数实现
......
throw(int类型)
throw(string类型)
throw(char类型)//想抛吗,估计抛不出来的,呵呵~~~~
......
}
这样,就保证我们在函数中只能抛出类型为int,和string的异常。

 

3:异常和继承
看代码先
#i nclude <iostream>
#i nclude <string>
#i nclude <math.h>
using namespace std;
class triangle :public exception//定义一个三角形的类
{
public :
float a,b,c,d;
float s;
public:
triangle()
{}
triangle(float a1,float b1,float c1)
{
   a=a1;
   b=b1;
   c=c1;
}
void judgment()   throw(exception)//判断是否是三角形
{
   if((a+b)<c ||(a+c)<b || (c+b)<a)//任意两边和小于第三边,就不是三角形
   {
     throw exception("不是三角形,玩我呀大哥");
   }
}
void dimension()//计算面积
{
   d=(a+b+c)/2;         //海伦公式
   s=sqrt(d*(d-a)*(d-b)*(d-c));
}
};
void main()
{

 

triangle a(7,2,3);

 

try
{
a.judgment();
a.dimension();
     cout<<"三角形a的面积为: "<<a.s<<endl;
}
catch(exception &e)
{
cout<<e.what()<<endl;
}

 

}

 

上诉代码写的就是异常的继承,triangle继承自exceprion类,exceprion是c++类库的一个标准异常类,triangle类继承了对异常的处理,比如语句throw exception("不是三角形,玩我呀大哥");,这里抛出的是一个exception类型的异常,我们在接受的时候就要用catch (exception &e)来接受,并且使用了一个exption提供的一个what方法,来输入异常描述。
我们也可以不用类库中的exception类,自己来写一个异常处理的类。
下面是我写的一个功能很简单的异常处理类,我把它做为一个基类,用triangle来继承它
#i nclude <iostream>
#i nclude <string>
#i nclude <math.h>
using namespace std;
class exec
{
private:
string error;
public:
exec()
{}
exec(string err)
{
error=err;
}
string geterr()
{
   return error;
}

 

};

 


class triangle :public exec//定义一个三角形的类
{
public :
float a,b,c,d;
float s;
public:
triangle()
{}
triangle(float a1,float b1,float c1)
{
   a=a1;
   b=b1;
   c=c1;
}
void judgment()   throw(exec)//判断是否是三角形
{
   if((a+b)<c ||(a+c)<b || (c+b)<a)//任意两边和小于第三边,就不是三角形
   {
     throw (exec("不是三角形,你玩我呀大哥"));
   }
}
void dimension()//计算面积
{
   d=(a+b+c)/2;         //海伦公式
   s=sqrt(d*(d-a)*(d-b)*(d-c));
}
};
void main()
{

 

triangle a(7,2,3);

 

try
{
a.judgment();
a.dimension();
     cout<<"三角形a的面积为: "<<a.s<<endl;
}
catch(exec &e)
{
cout<<e.geterr()<<endl;
}

 

}

 

exec类就可以说是一个异常处理的类(我是专为异常处理写的),triangle 继承自它。我运行了一下,效果和上面用exception的效果是一样的。不过我写的就,哎~不说也罢

   以上就是我的一点关于异常处理的一点小小的学习感触,同志们,踩着我的肩膀上吧。砖头,就拿去扔别人吧!