Re: [問題] 程式的例外
我不太肯定自己的想法是不是正確的,所以若有錯誤請各位幫忙指正。
首先,在 Java 中 Exception 有兩種,Check Exception 與 Uncheck Exception,
Check Exception 是那些必須使用 try-catch 包住或是宣告 throws 的 exceptions,
常見的有 IOException, InterruptedException, ... 等。
Uncheck Exception 則是相反,不需要 programmer 自行處理,程式也能夠 compile,
常見的像是 IndexOutOfBoundsException, NullPointerException, ... 等。
而書上提到的例子,NumberFormatException 是屬於 Uncheck Exception。
The Java Programming Language (Gosling, Arnold, and Holmes) 提到:
Unchecked runtime exceptions represent conditions that,
generally speaking, reflect errors in your program's logic
and **cannot be reasonably recovered** from at run time.
所以在你舉的這個例子上,其實就如同你所說,不應該使用 exception handling,
而應該更主動的避免這樣的情形發生。
但是,要如何正確的檢查使用者輸入的字串合不合法 (是否為 int) 呢?
即使使用者輸入的全是數字,也會有 overflow 的可能,要正確判斷並不是那麼容易。
在處理字串轉數字的這個議題上,特別是在 5.0 之前,
老實說我覺得最適合的方法就是用 exception handling,
不過基本上我是把這視為特殊狀況。
註 1: 在 C# 中有 tryParse() 可以回傳 boolean 檢查是否 parse 成功,
我覺得是個不錯的方式,不過用到了 Java 所沒有的 call by output。
註 2: Java 5.0 開始,Scanner.hasNextInt() 也算是解決了,
但也就 Scanner 能用。
Check Exception 正好相反,多半是那些你沒有辦法主動偵測、提前避免的狀況,
舉個例子,Server/Client 架構的程式,
在 Client 斷線時,Server 會收到 SocketException。
Exception 是 "例外" 而不是 "錯誤",
在我看來 exception handling 比較像是一種流程控制。
---
void exp() {
if (...) {
throw new Exception();
}
}
void bar() {
while (...) {
exp();
}
}
void foo() {
try {
bar();
} catch (Exception e) {
// handle it
}
}
---
把上述程式改成沒有 exception 的版本的版本:
---
int exp() {
if (...) {
return -1;
}
return 0;
}
int bar() {
while (...) {
int r = exp();
if (r==-1) return -1;
}
}
void foo() {
int r = bar();
if (r==-1) {
// handle it
}
}
---
這還只是比較簡單的狀況,如果進入的 function/method 更多層,
處理的 exception 更多時,就能夠更加體現 Exception handling 的簡潔。
※ 引述《Shrugg (淚眼問花花不語)》之銘言:
: 想請問一個一直都沒辦法在邏輯上說服自己的觀念性問題
: 參考資料都說,程式的例外是用來擷取runtime時的例外情形,用來攔截例外的發生的.
: 可是要是已經知道會有那些例外可能發生,
: 設計程式時我們不是就會把限制條件給加上去了,
: 根本不用等到例外發生了再來攔截吧?
: Runtime會發生的例外都是設計程式時根本沒想到的,既然沒想到,
: 為什麼會知道要怎麼去預防呢?
: 像旗標的Java2第十四章以一個使用者輸入錯誤當例子,程式例只能輸入數字
: 但當使用者輸入字串時就會是一個例外,所以程式安排這邊設計一個攔截字串例外
: 發生時的處理.
: 但是假設我是這個程式的開發者
: 我要是一開始就知道這個例外的存在,我就會設條件讓使用者不能輸入數字以外的資料了
: 如果我連這個例外都沒有預估到,我又怎麼會知道要去攔截這個例外呢?
: 希望有人知道我在說甚麼
--
※ 發信站: 批踢踢實業坊(ptt.cc)
◆ From: 114.34.7.189
討論串 (同標題文章)