1. 异常
1.1 异常的抛出
异常抛出使用throw关键字,使用语法为:
throw 异常
异常是个对象,如int I =1; throw I等。也可以自定义一个异常类,在必要的时候抛出该异常类的实例:
class myException{};
throw myException();//这里不能使用throw myException;
也可以使用throw new myException(),这里返回的是一个指针,catch时参数就不一样了。
1.2 try块
try块用于捕获异常,所以它必须包围能抛出的异常语句。Try后是一组处理代码,称之为catch子句,如:
try{ …
throw string(“internal error: ..”); //自定义的异常,异常为字符串类型
…
}
catch( string exceptionMsg){ //处理字符串类型的异常}
catch(const statsException &statsExcep){…}
catch(…){//处理所有异常,但是它不能访问异常对象}
如果抛出的是一个指针,如:
throw new string(“hello”);
那么catch的参数应为:
catch(string *msg)
{
cout << msg->c_str() << endl;
delete msg;
}
如果在一个捕获语句中
1.3 异常对象
catch子句的异常声明可以是一个类型声明或者对象声明,在抛出异常时最好把出错信息或者一些环境信息保存在异常对象中返回,如果仅是按值传递的异常对象的返回可能要经过二次对象的拷贝,一次是将异常抛出try块时,另一处是进入catch语句时,因此它会消耗很多资源。
如果采取以下结构的catch:
throw string(“hello”);
catch(string &msg)
{
cout << msg.c_str() << endl;
}
只需拷贝一次,即异常抛出时对异常对象进行了拷贝,进入catch子句后只是对该拷贝引用的访问,而没有再进行第二次拷贝。
如果采用以下结构的catch,那么一次拷贝都不需要了:
throw new string(“hello”);
catch(string *msg)
{
cout << msg->c_str() << endl;
delete msg;
}
在抛出异常时,异常对象是在堆中建立的,抛出的是该对象的指针的拷贝,进入catch后又对该指针进行了拷贝,即对异常对象的指针进行了两次拷贝,但对异常对象本身没有进行拷贝。
如果使用以下结构,仅对异常对象的指针进行了一次拷贝,对异常对象不拷贝:
throw new string(“hello”);
catch(string* &msg)
{
cout << msg->c_str() << endl;
delete msg;
}
以上代码省略了try块。
如果在一个catch中不能完全处理指定的异常,应将它重新抛出,重新抛出的语句为:
throw; //不需要在throw中加上异常对象,它会抛出原来的那个异常对象;
如果想再catch中修改异常对象中的信息,在catch中的参数应是引用类型,这和一般函数参数传递一样的道理。
还有一个特殊的catch,就是catch(…),这种catch会捕获所有类型的异常。
c++入门学习(异常)
最新推荐文章于 2024-01-24 16:38:47 发布