0

私は、Javaクラスが実装する抽象メソッドの意味についてかなり混乱しています。

たとえば、次のことを考慮してください。

interface Programmer {
    Object program();
}

class Linus implements Programmer {
    public String program() {
        return "goto end;";
    }
}

public class Main {
    public static void main(String[] args) {
        System.out.println(new Linus().program());
    }
}

オブジェクトがLinus.program()から来ることを期待するものはすべて、オブジェクト(具体的には文字列)を取得するため、これは明らかに受け入れられます。

しかし今これを考慮してください:

interface OS {
    void run(String code);
}

class Linux implements OS {
    public void run(Object code) {
        System.out.println("Hello world");
    }
}

public class Main {
    public static void main(String[] args) {
    new Linux().run("print 'Hello world'");
    }
}

これはコンパイルに失敗し、エラーが発生します。

The type Linux must implement the inherited abstract method OS.run(String)

これで、OSインターフェイスの任意のインスタンスに文字列を渡すことができると期待できますが、Linuxでも確実にそれを行うことができます。

2番目のものがコンパイルに失敗する理由はわかりません。Javaに2番目のプログラムをコンパイルさせた結果のうち、これを禁止する何かが欠けているのでしょうか。

4

3 に答える 3

5

2番目のケースで行っているのは、メソッドのオーバーロードです。
メソッドのシグネチャは「method-name」と「引数の数とタイプ」
です。2番目のケースでは、コンパイラが別のメソッドである引数のタイプを変更し、抽象化された(実装されていない)メソッドを実装するように求めます。また、インターフェースに存在するメソッドを実装するとpublic void run(String code)、このメソッドpublic void run(Object code)はオーバーロードされたメソッドとして扱われます。

注:メソッドのオーバーライドは、メソッドの戻りタイプに基づくことはありません。リターンタイプはメソッドのシグネチャとは見なされないため

于 2013-03-09T09:06:24.453 に答える
0

Stringクラスのインスタンスの代わりに基本クラスObjectのインスタンスを渡すことはできませんが、その逆は有効です。インターフェイスOSでは、runメソッドのパラメータはString型であり、実装クラスでは、許可されていないObject型のパラメータを一般化しています。したがって、コンパイラは文句を言います。

于 2013-03-09T09:09:44.890 に答える
0

「これで、OSインターフェイスの任意のインスタンスに文字列を渡すことができると期待できます。Linuxでも確実にそれを行うことができます。」=>問題は、できることですが、必須ではありません。

これを考慮してください。Linuxバージョンのメソッドはオブジェクトをパラメーターとして受け取るため、たとえば、コレクションを渡そうとすることができます。したがって、パラメータを文字列に明示的に制限するインターフェイスを尊重することはできません。そのため、LinuxバージョンのメソッドはOSバージョンの「子」とは見なされません。

また、インターフェイスの各メソッドには「子」が必要であるため、コンパイラは、OS.run(String)の「子」を実装していないと文句を言います。

于 2013-03-09T09:18:01.120 に答える