私のJava言語の理解に基づいて、静的変数はで初期化できますstatic initialization block
。
ただし、これを実際に実装しようとすると(static
変数final
も)、以下のスクリーンショットに示すエラーが発生します。
はい、もちろん:static final
変数は静的ブロックで初期化できますが....その例では暗黙のGOTOtry/catch
があります(本質的には「何か悪いことが起こった場合のGOTOキャッチ」です)。
例外がスローされた場合、final
変数は初期化されません。
静的構造の使用は、オブジェクト指向の教義に反することに注意してください。テストが複雑になり、デバッグが難しくなる可能性があります。
これを行うことはできますが、例外をスローして静的ブロックを終了する必要があります。キャッチされた例外または新しい例外を再スローできます。通常、この例外はである必要がありますRuntimeException
。ブロックException
内からスローされる可能性のある、一般的ではあるがより具体的な例外を実際にキャッチする必要はありません。try
最後に、静的初期化子が例外をスローすると、JVMはクラスの初期化を1回だけ試行するため、その特定の実行中にクラスを使用できなくなります。その後、このクラスを使用しようとすると、などの別の例外が発生しNoClassDefFoundError
ます。
したがって、動作するには、イニシャライザは次のように読み取る必要があります。
static {
try {
...
} catch (Exception e) {
e.PrintStackTrace();
throw new InitializationFailedException("Could not init class.", e);
}
}
InitializationFailedException
それがカスタムであると仮定しRuntimeException
ますが、既存のものを使用することができます。
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;
}
}
}
アップストリームがExceptionInInitializationErrorまたは一般的な例外のいずれかをキャッチする位置にない場合、プログラムはmyVarを使用しようとしないでください。ただし、それらがキャッチされてプログラムが終了しない場合は、myVarNullPointerExceptions
がnullになるのを監視して処理するようにコーディングする必要があります(または、すべてが出てくることに満足しています)。
これを処理する良い方法があるかどうかはわかりません。
宣言をfinallyブロックに入れることができますか?
try {
//load file
} catch(IOException e) {
// horay
} finally {
HOST=config.get......
}