23

Javaの例外checkedとの違いを理解するのに問題があります。unchecked

  1. まず、checked例外はコンパイル時に異常を探すことになっています。さまざまなソースで提供されている例では、データベース接続、ファイル処理などを挙げていますが、unchecked例外は、配列の範囲を超えたインデックス作成など、プログラマー側のエラーを探すことになっています。

逆にすべきではありませんか?つまり、データベース接続は実行時に行われますよね?ファイル処理についても同様です。コンパイル時にファイルハンドルを開かないのに、コンパイル時に発生する可能性のあるエラーが検索されるのはなぜですか?一方、その範囲を超える配列のインデックス作成はプログラムですでに行われており、コンパイル時にチェックできます(実行時にユーザーが異常なインデックスを指定した場合は、実行時に問題ありません)。問題)。ここで何が欠けていますか?

RunTimeException2次に、それ自体がuncheckedサブクラスExceptionである場合、どのようにできcheckedますか?これはどういう意味ですか?

checkedハーバート・シルトの本で、例外の使用法を説明する例を見つけました。

class ThrowsDemo {
   public static char prompt(String str)
      throws java.io.IOException {
  System.out.print(str + ": ");
  return (char) System.in.read();
  }
  public static void main(String args[]) {
    char ch;
    try {
      ch = prompt("Enter a letter");
    }
    catch(java.io.IOException exc) {
     System.out.println("I/O exception occurred.");
     ch = 'X';
    }
    System.out.println("You pressed " + ch);
    }
}

throwsここで条項は必要ですか?このようなステートメントで通常どおりに実行できないのはなぜですかtry-catch(申し訳ありませんが、のシミュレーション方法がわからないIO Exceptionため、自分で確認できませんでした!):

class ThrowsDemo {
   public static char prompt(String str)  {
     System.out.print(str + ": ");
     return (char) System.in.read();
  }
  public static void main(String args[]) {
    char ch;
    try {
      ch = prompt("Enter a letter");
    }
    catch(java.io.IOException exc) {
     System.out.println("I/O exception occurred.");
     ch = 'X';
    }
    System.out.println("You pressed " + ch);
    }
}
4

8 に答える 8

29

CheckedExceptionは呼び出し元が処理する必要がありますが、Unchecked例外は処理しません。

したがって、アプリケーションを設計するときは、管理している例外的な状況の種類を念頭に置く必要があります。

たとえば、ユーザー入力の有効性をチェックする検証メソッドを設計する場合、呼び出し元は検証例外をチェックし、見栄えの良い方法でエラーをユーザーに表示する必要があることがわかります。これはチェックされた例外である必要があります。

または、回復可能な例外的な状態の場合:ロードバランサーがあり、「n」サーバーの1つがダウンしていることを呼び出し元に通知したい場合、呼び出し元はインシデントを回復してメッセージを別のサーバーに再ルーティングする必要があります。呼び出し元(クライアント)がエラーを回復しようとすることが重要であり、エラーによってプログラムフローが中断されないようにすることが重要であるため、これはチェック済みの例外である必要があります。

代わりに、発生してはならない、および/または代わりにプログラムを中断する必要がある多くの条件があります。たとえば、プログラミングエラー(ゼロ除算、nullポインター例外など)、APIの誤った使用法(IllegalStateException、OperationNotSupportedException)、ハードウェアクラッシュ、または回復できない(サーバーへの接続が失われた)マイナーな状況などです。または終末:-); このような場合、通常の処理では、コードの最も外側のブロックに例外が到達し、予測できないエラーが発生したことをユーザーに表示し、アプリケーションは続行するために何もできなくなります。これは致命的な状態であるため、ログに印刷するか、ユーザーインターフェイスでユーザーに表示するだけです。そのような場合、例外をキャッチするのは間違っています。なぜなら、例外をキャッチした後、さらなる損害を避けるためにプログラムを手動で停止する必要があります。したがって、ある種の例外を「ファンにヒット」させる方がよいかもしれません:)

これらの理由により、JREでもチェックされていない例外がいくつかあります。OutOfMemoryError(回復不能)、NullPointerException(修正が必要なバグ)、ArrayIndexOutOfBoundsException(別のバグ例)などです。

個人的には、SQLExceptionもチェックを外す必要があると思います。これは、プログラムのバグ、またはデータベースへの接続の問題を示しているためです。しかし、実際には管理方法の手がかりがないという例外が発生する例はたくさんあります(RemoteException)。

例外を処理する最良の方法は、例外を回復または管理できる場合は、それを処理することです。それ以外の場合は、例外を無視します。他の誰かが処理する必要があります。あなたが最後の「他の誰か」であり、例外を処理する方法がわからない場合は、それを表示するだけです(ログまたはUIに表示)。

于 2012-12-23T15:33:55.370 に答える
8
  1. throws句でチェックされていない例外を宣言する必要はありません。ただし、チェックされた例外を宣言する必要があります。
  2. RuntimeExceptionおよびError、およびそれらのすべてのサブクラス(など)はIllegalArgumentExceptionStackOverflowError未解決の例外です。他のサブクラスとはRuntimeException異なり、チェックされていないという事実は仕様によるものです。Throwable
  3. 「コンパイル時の例外」などはありません。

より一般的には、JVMエラーまたはプログラマーエラーのいずれかが発生した場合に、チェックされていない例外がスローされると見なされます。このような有名な例外の1つNullPointerExceptionは、のサブクラスであるNPEと略されることが多いRuntimeExceptionため、チェックされていません。

チェックされていない例外とチェックされている例外のもう1つの非常に重要な違いは、try-catchブロック内で、チェックされていない例外をキャッチする場合は、明示的にキャッチする必要があることです

最後の注意:例外クラスE1と拡張がある場合E2、キャッチおよび/またはスローもキャッチ/スローします。これは、チェックされた例外とチェックされていない例外の両方を表します。これはブロックに影響を及ぼします。キャッチとを区別する場合は、最初にキャッチする必要があります。E2E1E1E2catchE2E1E2

例えば:

// IllegalArgumentException is unchecked, no need to declare it
public void illegal()
{
    throw new IllegalArgumentException("meh");
}

// IOException is a checked exception, it must be declared
public void ioerror()
    throws IOException
{
    throw new IOException("meh");
}

// Sample code using illegal(): if you want to catch IllegalArgumentException,
// you must do so explicitly. Not catching it is not considered an error
public void f()
{
    try {
        illegal();
    } catch (IllegalArgumentException e) { // Explicit catch!
        doSomething();
    }
}

これが物事をより明確にすることを願っています...

于 2012-12-23T14:36:57.423 に答える
7
  1. いいえ。すべての例外は実行時に発生します。チェックされた例外は、呼び出し元がそれらを処理または宣言することを強制する例外です。これらは通常、プログラマーのエラー(ファイルが存在しない、ネットワーク接続の問題など)が原因ではない、回復可能なエラーを通知することを目的としています。ランタイム例外は通常、回復不能なエラーを通知することを目的としています。それらは、呼び出し元にそれらを処理または宣言するように強制しません。そして、それらの多くは確かにプログラミングエラー(NullPointerExceptionなど)を示しています。

  2. これが、JLSがチェックされていない例外を定義する方法であるためです。RuntimeExceptionであるかそれを拡張する例外であり、それ自体がExceptionを拡張します。単一の継承ルートを使用すると、単一のcatch句で発生する可能性のあるすべての例外をハンドロングできます。

あなたの例に関して:はい、IOExceptionはチェックされた例外であり、メソッド内のコードはそれをスローする可能性があるため、throws句は必須です。

于 2012-12-23T14:40:28.897 に答える
2

コンパイラは、メソッドが宣言しなかった場合にのみ、チェックされた例外をスローできないようにします。コンパイラによるこのようなチェックは、引用した例(データベース接続、ファイルの欠落など)など、プログラマーの制御外で発生する例外に対して実行する必要があると一般的に考えられています。チェックされていない例外は「発生するはずがない」ので、コンパイラはそれらを宣言するように強制しません。

シミュレーションIOExceptionやその他に関しては、それは些細なことです。

throw new IOException();

あなたの例では、promptメソッドがをスローする可能性があるIOExceptionため、それを宣言する必要があります。これは、メソッドを呼び出した時点での例外の処理方法とは関係ありません。

RuntimeExceptionはのサブクラスであり、1つの句Exceptionですべての例外をキャッチするのに便利です。catch Exceptionこれは別の方法で設計されている可能性があります。Javaの例外クラス階層は混乱しています。

于 2012-12-23T14:37:55.253 に答える
1

ここにthrows句を入れないと、このエラーが発生します

ThrowsDemo.java:5:報告されていない例外java.io.IOException; キャッチするか、スローするように宣言する必要がありますreturn(char)System.in.read();

したがって、必要に応じて句をスローします。

于 2012-12-23T14:38:42.437 に答える
1

チェックされた例外とチェックされていない例外の5つの例。

Unchecked Exception
   -- NullPointerException
   -- ArrayIndexOutofBound
   -- IllegalArgument Exception
   -- ClassCastException
   -- IllegalStateException
   -- ConcurrentModificationException

Checked Exception Five Example
   -- FileNotFoundException
   -- ParseException
   -- ClassNotFoundException
   -- CloneNotSupportException
   -- SQLException
于 2016-03-24T15:15:51.807 に答える
0

チェックされた例外とチェックされていない例外

例外には、チェックされた例外とチェックされていない例外の2種類があります。チェックされた例外とチェックされていない例外の主な違いは、チェックされた例外はコンパイル時にチェックされ、チェックされていない例外は実行時にチェックされることです。

明確なアイデアを得るためにこの記事を読んでください。

于 2014-08-22T05:52:06.697 に答える
0

詳細

クライアントコードが例外の情報に基づいて有用な回復アクションを実行できる場合は、チェックされた例外を使用します。クライアントコードが何もできない場合は、チェックされていない例外を使用します。たとえば、クライアントコードがSQLExceptionから回復できる場合は、SQLExceptionを別のチェックされた例外に変換し、クライアントコードがそれについて何もできない場合は、SQLExceptionをチェックされていない(つまりRuntimeException)例外に変換します。

于 2015-12-23T13:23:39.357 に答える