l

2013年11月7日 星期四

例外處理的四種Context(1):Exception Context

Nov. 05 15:14~16:50

螢幕快照 2013-11-05 下午4.49.38

地圖與現在位置的關係,也是一種context。

 

Context這個字,在軟體開發這個領域中用得非常多。這個字根據它在文章中出現的用法,大致可以翻譯成「脈絡」、「情境」、「上下文」、「環境」等。Teddy之前在介紹Design Pattern的時候也說明過Context的意義,這一系列的主題要解釋在例外處理的四種不同的Context:exception contextlocal contextobject contextapplication context。今天先介紹exception context。

***

Exception Context

Exception context是當例外發生的時候,例外處理者(exception handler)可獲得的例外相關資訊。這些資訊可以透過程式語言執行環境傳入,例如產生例外的method名稱、產生例外的程式碼行號、例外產生當時的method呼叫堆疊資訊(stack trace)。

在下列Java程式範例,執行main()會讓Java虛擬機器丟出一個RuntimeException。

螢幕快照 2013-11-05 下午3.49.29

 

第24行e.printStackTrace()程式碼會印出由Java虛擬機器所準備好的exception context,如下圖所示,可以從中得知main()程式呼叫了methodA(),然後methodA()呼叫了methodB(),再然後methodB()呼叫了methodC。最後,由methodC()丟出了一個RuntimeException,由ExceptionContext.java這隻程式的第14行所丟出。

螢幕快照 2013-11-05 下午3.50.26

***

Exception context也可以由例外產生者(signaler)傳入,例如鄉民們可以在Java語言中可以透過「例外串接」(exception chaining)的方法,把產生某個例外的根本原因(root cause,另外一個例外物件)一併傳給例外處理者。如下圖程式碼所示,第16~18行的例外處理程式,當捕捉到IOException之後,產生一個新的NotEnoughDiskSpaceException,並且把捕捉到的IOException當成參數傳給NotEnoughDiskSpaceException的建構元(constructor)。

螢幕快照 2013-11-05 下午4.19.33

 

執行main()的結果,可以看到stack trace多了一個Cause by的資訊,這就是在第17行傳給NotEnoughDiskSpaceException的建構元的那一個IOException。

螢幕快照 2013-11-05 下午4.22.33

***

Java語言預設的Throwable類別是所有例外類別的父類別,看一下Throwable的建構元:

  • Exception()
  • Exception(String message) 
  • Exception(String message, Throwable cause)
  • Exception(Throwable cause)


基本上只允許例外產生者自行傳入一個字串和一個產生該例外的cause exception物件。也就是說,在Java語言中除非設計自己的例外物件,否則在預設的情況下例外產生者可以透過exception context傳遞給例外處理者的資訊很有限。

關於這個限制Teddy在《Implementation Patterns: Variable State》曾經探討過,微軟的例外類別因為支援了Variable State這個pattern,使得例外產生者可以透過exception context傳遞任意資料給例外處理者。

***

友藏內心獨白:Exception context資料的豐富性,會影響例外處理程式的能力。

沒有留言:

張貼留言