2016-04-29 36 views
1

經過長時間的差距,我重新開始用Java編寫代碼 - 在過去的幾年中,我的大部分編碼工作都在PHP & JavaScript中 - 我發現我必須更加努力才能滿足Java編譯器對變量作用域和異常處理等問題要嚴格得多。引起我一些麻煩的一段代碼如下所示Java範圍界定和可視性規則

File file = new File(path, fname); 
FileOutputStream stream = null; 
try 
{ 
stream = new FileOutputStream(file); 
stream.write(tosave.getBytes()); 
} 
finally 
{ 
try 
{ 
    if (null != stream) {stream.close();} 
    return true; 
} 
catch(Exception e){return false;}   
} 

這被編譯器接受。但是,在我來到這裏之前,我遇到過幾個問題。

  • 第一次嘗試:沒有捕捉塊。編譯器拒絕玩球,因爲它希望我處理無法創建FileOutputStream的可能性。同樣寫入該流。我理解這個推理背後的邏輯並且喜歡它。
  • 第二次嘗試:捕獲塊,但...:我宣佈並創建stream變量INSIDE try塊。編譯器再次拋出一個抖動 - stream變量在finally塊中超出範圍。

正如你所看到的,我已經通過在try塊之上聲明stream並將其初始化爲空來解決問題。

This Works。但是,鑑於我的Java技能有多麼生疏,我想我會問:有沒有正確的方式來編寫這樣的代碼?

+1

你可以嘗試使用與資源使用Java 7 onwards..Just一些糖,還是更少的代碼 – zencv

+0

http://docs.oracle.com/javase/tutorial/essential/exceptions /tryResourceClose.html –

回答

3

現代Java版本(自Java 7以來)處理這種情況的慣用方式是使用try-with-resource塊來處理所有難看的關閉「邏輯」。你仍然必須捕捉異常或向上傳播它,但這是一個相對較小的問題。考慮以下幾點:

public static boolean writeToFile(String path, String fname) { 
    File file = new File(path, fname); 
    try (FileOutputStream stream = new FileOutputStream(file)) { 
     stream.write(tosave.getBytes()); 
    } catch (IOException e) { 
     // Should probably log the exception too 
     return false; 
    } 
    return true; 
} 
+0

謝謝你的各種答案 - 我只能接受一個:-)。我不知道試用資源塊。我想我上一次做Java它仍然在版本6-- – DroidOS

1

你可以簡單地使用下面的代碼片段:

try (FileOutputStream stream = new FileOutputStream(file)){ 
    stream.write(tosave.getBytes()); 
}catch(IOException e) { 
    e.printStackTrace(); 
    return false; 
} 

return true; 

這是在Java中引入的新功能(try-with-resources Statement)7.

0

「正確」 的方法是使用Java 7的try with resources。它已經很長一段時間了,但它很好地清理了這種樣板代碼。如果你是卡在較早的Java版本

真倒黴:)

1

我認爲你得到的東西,並不重要掛斷了電話。是的,在某些情況下編碼try/catch/finally很重要,因爲你實際上需要做一些事情來修復錯誤。

但是,對於打開/關閉文件,您不想爲了滿足編譯器而陷入困境。代碼可讀性更重要。

如何:

String path="somepath"; 
String fname="somefile"; 
String tosave="somedata"; 
try { 
    File file = new File(path, fname); 
    FileOutputStream stream = new FileOutputStream(file); 
    stream.write(tosave.getBytes()); 
    stream.close(); 
} 
catch (Exception e) { 
    e.printStackTrace(); 
    return false; 
} 
return true; 
+0

由於您的評論我正在提出您的答案 - _Code可讀性更重要_ - 一個非常有效的觀點。我應該提到的是,這裏的上下文是Android的一個Phonegap插件,寫入內部存儲。我懷疑設備拒絕讓文件被創建/寫入是有實際可能的。 – DroidOS

+0

謝謝!我們都知道這很容易'發現'錯誤....但是,你會怎麼做? –