3

私はジェネリックについて多くのことを読んできましたが、Java で単純な階層を実装する際にいくつかの基本的な問題が残っています。目標は、同じクラスの 2 つのオブジェクトを比較する抽象メソッドを定義することです。オブジェクトが異なるクラスのものである場合は、false を返す必要があります。例:

抽象クラス Sound を定義します

abstract class Sound{
    public boolean check(Sound d){return false;};
}

Sound を拡張するいくつかのクラスと、それから拡張される別の抽象クラス (Alarm など)

abstract class Alarm extends Sound{
    @Override
    public boolean check(Alarm d){//Do something and return boolean};
}

そこから拡張するいくつかのクラスがあります。

簡単な解決策は、示されているようにメソッドを定義することであり、それは機能しますが、階層を強制するより良い方法があると感じているため、Sound クラスは、メソッドが同じクラスのパラメーターでのみ使用される必要があることを定義します。

私がジェネリックで試したこと:

abstract class Sound{
    public <T extends Sound> boolean check(T d){return false;};
}

abstract class Alarm extends Sound{
    @Override
    public <T extends Alarm> boolean check(T d){//Do something and return boolean};
}

また

abstract class Alarm extends Sound{
    @Override
    public boolean check(Alarm d){//check and return boolean};
}

Java が文句を言うのは、コンパイラに対して Alarm のチェック メソッドをオーバーライドしていないためです。何が欠けている可能性があるかについての手がかりはありますか?

4

3 に答える 3

6

あなたの考えは本質的に間違っています。
ジェネリック メソッドのポイントは、呼び出し元が制約を満たす任意の型を指定できることです。
つまり、呼び出し元は次のように記述できます。

sound.<NonAlarm> check(...);

NonAlarmを継承するクラスはどこにありますかSound

AlarminheritsであるためSound、そのcheck()メソッドには同じ制約が必要です。

代わりに、 CRTPを使用できます。

public abstract class Sound<T extends Sound<T>> {
    public abstract boolean check(T d);
}

public class Alarm extends Sound<Alarm> {
    @Override
    public boolean check(Alarm d) { ... }
}
于 2012-11-28T18:08:25.053 に答える
0

次のようなものはどうですか:

interface ISound<T> {
    public boolean check(T d);
}

abstract class Alarm implements ISound<Alarm> {
    @Override
    public boolean check(Alarm d) { return true; };
}

(あなたの質問を正しく理解できたと思います!)

于 2012-11-28T18:10:53.090 に答える
-1

クラスを拡張していません!!

abstract class Alarm extends Sound {
}

これが正しい方法です...

于 2012-11-28T18:08:40.827 に答える