2013-04-20 58 views
5

我有兩個構造函數用於我的類,一個需要File對象,另一個需要String對象,我想使用this關鍵字。具有實現的功能是File作爲參數的函數,具有String的函數將調用this。現在我想檢查構造函數中的異常,其中需要String但我得到錯誤,應該是第一行this。如何檢查錯誤,然後致電this構造函數處理異常並使用此關鍵字Java

這裏是我的代碼:

public Test (String filename) { 
    if (filename == null) 
     throw new NullPointerException("The String you entered is null."); 
    if (filename.isEmpty()) 
     throw new IllegalArgumentException("The String you entered is empty."); 

    this(new File(filename)); // error 
} 

public Test (File f) { 
    /* implementation here */ 
} 

這是確切的錯誤:Constructor call must be the first statement in a constructor

+0

你得到什麼錯誤? – Thomas 2013-04-20 14:24:38

+0

發佈的代碼與您所描述的相反! – NINCOMPOOP 2013-04-20 14:24:40

回答

2

不幸的是,這是在Java中感謝他們的任意限制是不可能的。你有兩個主要的可能性。

更習慣的Java技術是將所有東西都包含在工廠函數中,這樣您就可以捕獲異常。工廠函數也很有用,因爲它們允許您以多態方式創建對象,並幫助隱藏實際創建對象的細節。

public static Test create(String filename){ 
    if (filename == null) 
     throw new NullPointerException("The String you entered is null."); 
    if (filename.isEmpty()) 
     throw new IllegalArgumentException("The String you entered is empty."); 
    return new Test(filename); 
} 

private Test (String filename) { 
    this(new File(filename)); 
} 

public Test (File f) { 
    /* implementation here */ 
} 

另一種選擇是在字節碼中寫入構造函數,其中不存在這樣的限制。不幸的是,字節碼的可讀性和可維護性較差,因此您可能希望最大限度地減少主要Java應用程序中字節碼的數量。您也可以使用非Java語言(如AspectJ)來執行此操作。

編輯:如果你實際上沒有試圖捕捉異常,那麼還有第三種可能性。您可以在超級構造函數調用之前插入任意代碼,方法是創建一個單獨的函數,該函數執行檢查,然後將其作爲虛構參數傳遞給超級構造函數調用。由於首先評估參數,您的代碼將首先運行,但這有些破綻。

public Test (String filename) { 
    this(doChecks(filename), new File(filename)); 
} 

private static Void doChecks(String filename){ 
    if (filename == null) 
     throw new NullPointerException("The String you entered is null."); 
    if (filename.isEmpty()) 
     throw new IllegalArgumentException("The String you entered is empty."); 
    return null; 
} 

public Test (Void dummy, File f) { 
    this(f); 
} 

public Test (File f) { 
    /* implementation here */ 
} 
+0

第一個選項,就像編寫一個'init'函數並使用它? – 2013-04-20 14:26:31

+0

我剛剛爲第三個選項添加了一個代碼示例。 – Antimony 2013-04-20 14:33:46

+0

*由於其任意限制,這在Java中是不可能的*:我想限制不是任意的;) – NINCOMPOOP 2013-04-20 14:36:06

0

不,您不能在致電this之前檢查錯誤。這是規範禁止的。事實上,你並不需要它。讓new File(filename)拋出異常。

編輯:我看到aizen92的評論:Actually that is what my constructor with the implementation has, it catches the exception may be thrown by file, so I just add the null exception and use this directly in my second constructor?

public Test (String filename) { 
    this((filename == null || filename.isEmpty()) ? null : new File(filename)); 
} 
+0

這會在'filename.isEmpty()'時拋出錯誤的異常類型。 – Antimony 2013-04-20 14:44:41

0

在我們使用this或構造super,無論是thissuper情況下應該是在構造函數中的第一條語句。如果你從特定的構造函數中拋出異常,那更好。

public Test (String filename) { 
    this(new File(filename)); 
} 

讓第二個構造函數處理任何異常,由傳遞null引起。

public Test (File file) { 
    // exception handling code 
    // or new instance creation 
} 
+0

其實這就是我的構造函數與實現,它捕獲異常可能會拋出的文件,所以我只是添加null異常,並使用'this'直接在我的第二個構造? – 2013-04-20 14:37:50