Java
 Computer >> コンピューター >  >> プログラミング >> Java

【Java】オーバーライドメソッドは、元のメソッドがスローする例外のスーパータイプをスローできるのか?

結論から言うと、スーパークラスのメソッドが特定の例外をスローしている場合、サブクラスでオーバーライドしたメソッドは、その例外のスーパータイプ(親クラス)をスローすることはできません

これはJavaの言語仕様による厳格なルールです。スーパークラス型の参照を通じてメソッドを呼び出すコードは、スーパークラスが宣言した例外だけを想定して記述されています。もしサブクラス側がより広い範囲のチェック例外をスローできるようになると、呼び出し側でその例外を捕捉できなくなり、型安全性が損なわれるためです。

具体例

以下の例では、スーパークラスの readFile() メソッドが FileNotFoundException 例外をスローしています。一方、サブクラスでオーバーライドされた readFile() メソッドは、FileNotFoundException のスーパータイプにあたる IOException をスローしようとしています。

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.Scanner;

abstract class Super {
    public String readFile(String path) throws FileNotFoundException {
        throw new FileNotFoundException();
    }
}

public class ExceptionsExample extends Super {
    @Override
    public String readFile(String path) throws IOException {
        // メソッド本体 ......&nbs p;  }
}

コンパイルエラーの内容

このプログラムをコンパイルすると、次のようなエラーが出力されます。

ExceptionsExample.java:13: error: readFile(String) in ExceptionsExample cannot override readFile(String) in Sup
    public String readFile(String path) throws IOException {
                 ^
overridden method does not throw IOException
1 error

エラーメッセージ「overridden method does not throw IOException」は、オーバーライド先のメソッドが IOException を宣言していないため、それをスローするオーバーライドは許可されないことを示しています。

ポイントまとめ

オーバーライド時の例外宣言に関するルールは以下の通りです。

  • スーパークラスのメソッドと同じ例外をスローできる。
  • スーパークラスがスローする例外のサブクラス(より具体的な例外)をスローできる。
  • オーバーライドメソッドで例外をまったくスローしないことも可能。
  • ただし、スーパークラスがスローする例外のスーパータイプ(より広いチェック例外)をスローすることはできない。

このルールを守ることで、ポリモーフィズムを利用しても呼び出し側が例外を確実にハンドリングできる、安全なコード設計になります。

  1. JavaのSwingUtilities.invokeLater()メソッドの使い方を徹底解説

    invokeLater()メソッドとはinvokeLater()メソッドは、SwingUtilitiesクラスが提供するstaticメソッドの一つで、AWTイベントディスパッチスレッド(Event Dispatch Thread)上でタスクを非同期に実行するために使用されます。このメソッドはSwingUtilities.invokeAndWait()とよく似た動作をしますが、大きな違いは、処理のリクエストをイベントキューに登録した後、すぐに呼び出し元へ制御を返すという点です。つまり、invokeLater()は引数で渡されたRunnableオブジェクト内のコードブロックの実行完了を待ちません。

  2. JavaでJPanelのpaintComponent()メソッドを実装する方法をわかりやすく解説

    JPanelはJavaにおける軽量コンテナであり、それ自体は不可視(インビジブル)なコンポーネントとして扱われます。デフォルトのレイアウトにはFlowLayoutが採用されています。JPanelを生成した後は、Containerクラスから継承されたadd()メソッドを呼び出すことで、ボタンやラベルなどの他のコンポーネントをJPanelオブジェクトに自由に追加できます。 paintComponent()メソッドとは このメソッドは、単なる背景色の描画にとどまらず、JPanel上に独自の図形や画像などを描画したい場合に必要となります。paintComponent()メソッドはすでにJPanelクラ