C++ Exception handling(异常处理) part1

程序中最常出现的两种错误为:

(1)逻辑错误(logic error, 亦被称为semantics errors)

()语法错误(syntax error)

逻辑错误源于对问题和解决方案的错误理解。  也就是说程序可以通过编译生成可执行文件。 但是运行的结果不符合预期。 因 semantics errors 的确认是非常tricky的。因为计算机不会产生任何error message。 It just do not do the right things。 

语法错误源于对语言本身的理解有误引起。 也就是说根本通不过编译, 无法生成可执行文件。 这属于 Compile time error, 当然也就无法生成可执行文件。 通过不断的调试, 测试, 我们可以检测到这些错误。

但是, 除了semantic errors 和Syntax error, 还有一种错误叫做run time error。 之所以叫做run time error, 是因为虽然程序通过了编译, 但是运行的时候出现了意外。These errors are called exceptions(异常)。

异常是程序运行时出现的反常现象。 异常通常包含:

(1)除0错误(division by 0)

(2)数组存取越界(access to an array outside of its bounds)

(3)内存或者磁盘空间不足 (exhaustion of the heap memory)


Q: 什么叫做异常处理(exception handling)

A: 在检测到程序中的exception, 然后进行处理议异常的过程(The special processing required after detection of an 
exception is called  exception handling)


Q: 什么叫做异常处理柄(exception  handler)

A: 就是执行议程处理工作的代码(The exception handling code unit), 即catch block。


Q: C++ 中, 异常处理的主要方法

A: 传统的处理异常的方法有(Traditional approaches):

    (1)直接退出程序(terminate): 例如使用函数exit(), abort() 等。

      (2) Return special values to indicate errors in a function(函数中返回特殊的值, 以表明错误)

      (3)Set global error bits and return normally (leaving the  system in an illegal state)

    除了传统的方法外, C++语言还提供了一些built-in features 用于raise 以及handle exceptions。

特点是:

(1)error handling code 和 ordinary code 分开

(2)自动的释放局部资源等等。


Q:C++ 异常处理的过程

A: (1)返现 可能产生异常的代码 中的异常(try内部)

     (2)抛出异常(throw关键字, throw an exception)

   (3)捕捉异常(catch关键字)

(4)在catch blocks 中, 处理异常。


不难看出, C++ 的异常处理机制try-throw-catch的triad(三重奏)。 

try 快内(里面含有normal code)的代码可能会产生错误(exception), 也可能不产生。 当异常被检测到的时候, try 块中使用throw语句抛出异常, 从而跳出try 快, 由catch快抓住, 从而进入对应的catch块进行异常处理。 注意, 异常其实是对象。 他们用于传输错误的信息。 如果抛出的异常的类型和catch语句中的catch-block-parameter 相匹配, 那么catch块执行一处理议程。 如果不匹配, 直接调用默认的abort() 函数, 程序被终止。 当没有异常发生的时候, 控制流程转到catch块之后执行。 即catch块被忽略了。 

不难理解为什么叫做try block, 因为try 块里面可能会发生异常, 我们只是try 一下。 try 块中有throw 语句, 用于抛出异常。注意, 我们可能有multiple tries and catches。


异常处理语法如下:




关于catch block:

catch(formal parameter), catch 吃一个形参(我们也可以pass by reference), 用于传进去异常。 值得注意的是:

(1)catch function can only have a single parameter。 即每一个catch只能有一个catch-block-parameter。

(2)parameter 既可以是一个built in type, 也可以是一个user-defined class。

(3)user-defined provides a way of passing multiple parameters

(4)参数可以是...(即形式是catch(...)), 这样, 我们可以catch所有的异常, 从而进行异常处理。 此时handler是一个catch-all handler。记住, catch(...)要放在所有的catch处理块的最后面。 把它放在任何一个catch快的前面, 都会阻碍那些块的议程捕捉。

(5)the formal parameter(形参) can be ignored by not providing a variable name(只给出异常的类型), 例如: catch(OException){...}。


一个需要注意的是,scope rules. 也就是发生异常, 在执行catch statement之前, try block中的所有变量将会被deallocated. 此时如果你想存取在try block中的变量的时候, make sure you declare that variable outside the try block。

处理完异常后, 执行catch block 后面(非catch)的语句。 


将异常(exceptions)绑定(binding)到handler的方法是使用throw语句:

throw(expression);


重新抛出异常:

在没有任何处理的情况下, 处理代码可能会重新抛出捕捉到的议程。 这是, 我们只要(当然此时我们在catch块中)调用throw, 而无需使用任何参数。 如下所示:

throw;

这将会使得引发当前异常 被抛到下一个try/catch 封闭序列中, 并被闭合的try 块后的catch语句捕捉。  当异常被重新抛出时, 它不会被同一个catch语句或者同组的任何一个catch块捕捉到,他只能被适当的外层的try/catch 序列捕捉到。

一个catch处理代码本身也可能检测到异常并抛出异常。 抛出的异常不会被同组的其他catch语句捕捉到, 它会被传递到下一个外层的try/catch 序列, 以进行处理。



如何匹配exceptions(matching exceptions):

(1)throws are matched to exception handlers whose formal parameters matches the type of  the thown expressions。

(2)A handler with type T matches an expressions of type T, const T, T&, or const T&。

(3) a handler with formal parameter that is a class type T maches any expression with class type T or whose type is a derived class of T。

(because  an object of a derived class is an object of its base class)。


最后, 关于throw exception object的几个considerations:

(1)It is a bad idea to throw an exception object that is allocated from the heap because the catcher has ro remember to de-allocate the object if you do so。

(如果忘记deallocate , 会造成memory leaking)

so throw the exception object  that is allocated from the stack because C++  will automatically de-allocate the object。

例如, throw StackExpression, 而非 throw new stcakException

还有一点:



最后, 说说standard exception:



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值