2010-02-26 42 views

Trả lời

33

Có tất nhiên: static final biến thể được khởi tạo trong một khối tĩnh nhưng .... bạn có các GOTO ẩn trong ví dụ đó (try/catch về bản chất là một 'GOTO' '' nếu có điều gì đó xấu xảy ra ').

Nếu ngoại lệ được ném, các biến số final của bạn sẽ không được khởi tạo.

Lưu ý rằng việc sử dụng các cấu trúc tĩnh đi ngược lại giáo điều hướng đối tượng. Nó có thể làm phức tạp thử nghiệm của bạn và làm cho việc gỡ lỗi trở nên khó khăn hơn.

+1

Tôi có thể ném ngoại lệ từ 'khối khởi tạo tĩnh'. Tôi có thể làm gì khi một mã trong 'khối khởi tạo tĩnh 'ném một số ngoại lệ mà tôi không muốn xử lý. –

+0

bạn có thể khởi tạo các biến bên ngoài khối try catch, ví dụ: làm ngoại lệ ném mã trong cố gắng nắm bắt và khởi tạo trong cuối cùng ... – awk

+3

@ Hawk: ông sẽ cần phải sử dụng người dân địa phương để làm nhiệm vụ nếu mã ném ngoại lệ là getString (...) gọi phương thức. –

17

Bạn có thể làm điều này nhưng bạn cần phải thoát khỏi khối tĩnh bằng cách ném một ngoại lệ - bạn có thể tính lại ngoại lệ đã bị bắt hoặc một ngoại lệ mới. Nói chung ngoại lệ này phải là RuntimeException. Bạn thực sự không nên nắm bắt một số chung Exception nhưng ngoại lệ cụ thể hơn có thể được ném từ bên trong khối try của bạn. Cuối cùng, nếu một bộ khởi tạo tĩnh ném một ngoại lệ thì nó sẽ làm cho lớp không sử dụng được trong suốt quá trình chạy cụ thể đó vì JVM sẽ chỉ cố gắng khởi tạo lớp của bạn một lần. Các nỗ lực tiếp theo để sử dụng lớp này sẽ dẫn đến một ngoại lệ khác, chẳng hạn như NoClassDefFoundError.

Vì vậy, để làm việc, khởi tạo bạn nên đọc một cái gì đó như thế này:

static { 
    try { 
     ... 
    } catch (Exception e) { 
     e.PrintStackTrace(); 
     throw new InitializationFailedException("Could not init class.", e); 
    } 
} 

Giả sử rằng InitializationFailedException là một phong tục RuntimeException, nhưng bạn có thể sử dụng hiện có.

+0

Không chắc chắn lý do tại sao có một cuộc bỏ phiếu xuống, xin vui lòng giải thích. –

0

Bạn có thể đặt tuyên bố trong khối cuối cùng không?

try { 
    //load file 
} catch(IOException e) { 
    // horay 
} finally { 
    HOST=config.get...... 
} 
+1

Điều này là không thể. – pvorb

8
public class MyClass 
{ 
    private static final SomeClass myVar; 

    static 
    { 
     Object obj = null; // You could use SomeClass, but I like Object so you can reuse it 
     try 
     { 
      obj = new SomeClass(...);  
     } 
     catch(WhateverException err) 
     { 
      // Possibly nested try-catches here if the first exception is recoverable... 
      // Print an error, log the error, do something with the error 
      throw new ExceptionInInitializerError(err); 
     } 
     finally 
     { 
      myVar = (SomeClass) obj; 
     } 
    } 
} 

Giả sử không có nơi thượng nguồn là ở một vị trí để bắt hoặc một ExceptionInInitializationError hoặc một vị tướng Exception sau đó chương trình sẽ không bao giờ cố gắng sử dụng myVar. Tuy nhiên, nếu những người bị bắt và chương trình không kết thúc, thì bạn cần mã để xem và xử lý myVar bị vô hiệu (hoặc hài lòng với NullPointerExceptions sắp ra mắt).

Tôi không chắc chắn có cách nào tốt để xử lý việc này.

+1

>>> _then bạn cần mã để xem và xử lý myVar là null_ Ở đây trình khởi tạo tĩnh ném ra một ngoại lệ ngăn cản lớp được nạp ở tất cả (và do đó các biến không thể tham chiếu uninitialized) do đó không cần phải lo lắng NPE (ngoại lệ con trỏ null) – sactiw

Các vấn đề liên quan