36

ワイルド カード パラメータを理解するのに本当に苦労しています。それに関していくつか質問があります。

  1. ?型パラメーターとして、メソッドでのみ使用できます。例:型パラメータとして printAll(MyList<? extends Serializable>)クラスを定義できません。?

  2. の上限が分かりました?printAll(MyList<? extends Serializable>)意味:「インターフェイスを実装するオブジェクトがある場合は出力されprintAllますMyListSerialzable。 」
    私はsuper. printAll(MyList<? super MyClass>)意味: "のオブジェクトまたは拡張するクラス(の子孫) がある場合にprintAll表示されます。MyListMyClassMyClassMyClass "

私が間違っていたところを修正してください。

つまり、ジェネリック クラスを定義するための型パラメーターとしてTor Eor Kor Vorのみを使用できます。メソッドでのみ使用できますN?


更新 1:

public void printAll(MyList<? super MyClass>){
    // code code code
}

Ivor Horton の本によれば、それが実装するインターフェイスまたはクラスのオブジェクトまたはいずれかがある場合、MyList<? super MyClass>印刷できることを意味します。つまり、下限です。継承階層の最後のクラスです。これは、私の最初の仮定が間違っていたことを意味します。MyListMyClassMyClass

したがって、MyClass次のように見える場合は次のようになります。

public class MyClass extends Thread implements ActionListener{
    // whatever
}

次に、次のprintAll()場合に出力され
ます 1.MyClassリストに のオブジェクト
があります 2.ThreadまたはActionListenerのオブジェクトがありますList


更新 2:

したがって、質問に対する多くの回答を読んだ後、私の理解は次のとおりです。

  1. ? extends Tを拡張する任意のクラスをT意味します。したがって、 の子をT参照しています。したがって、T上限です。継承階層の最上位クラス

  2. ? super Tのクラス/インターフェースをsuper意味Tします。したがって、 のすべての親をT参照しています。Tしたがって、 は下限です。継承階層の最下位クラス

4

6 に答える 6

16

まず、TまたはEまたはK何かは固定された名前ではありません。それらは単なる型変数であり、それらの名前を決定します。TEKは単なる例ですが、それをFoo何と呼んでもかまいません。

最初の質問に進みます。ワイルドカード?は「任意で不明な」型、未指定の型を表すため、未指定の型に対してジェネリック クラスを宣言しても意味がありません。タイプを気にしない場合は、メソッドのパラメーターまたは変数にワイルドカードを使用すると便利です。

2 番目の質問について: 下限により、ジェネリック メソッドの柔軟性がさらに高まります。extendsとの両方superが反対です。

  • ? extends T: のサブタイプである不明なタイプT
  • ? super T: のスーパー タイプである未知のタイプT

後者は、T と互換性のある型を受け入れたい場合に役立ちます (つまり、T はその型です)。実際の例はここにあります。

于 2013-11-05T18:17:46.027 に答える
1

下限: 「super」キーワードの後に​​記載されているクラス、またはそのスーパー タイプのいずれかを使用できます。これは扱いにくい場合があります。以下の例に示すように、これらのスーパー タイプには、それらを継承する他の (完全に異なる) クラスが含まれる場合があります。

言う、

List<? super Car> cars = new ArrayList <Vehicle>();

プログラマーに次の書き込みを許可する必要があります。

cars.add(new Helicopter()); //Helicopter is a kind of Vehicle

これは明らかに許可されるべきではなく、下限を使用することの危険性を反映しています。

プログラマーは車両をリストに追加できますが、車両は一切追加できません。次のように、彼はそれをキャストして、Java に車の乗り物だけを追加していることを知らせる必要があります。

cars.add((Car) new Vehicle()); 
于 2019-11-29T15:23:01.467 に答える
0

superうーん、 ( )に関するあなたの発言printAll(MyList<? super MyClass>)は明確ではありません。つまり、Myclass が拡張されていると仮定すると、それObjectは可能であり、他には何もprintAll(MyList<MyClass>)できないということです....つまり、MyList のジェネリック型は MyClass のスーパークラス (サブクラスではない) でなければならないということです。printAll(MyList<Object>)これはあなたの言っていることと違います。

T、E、K、V、または N については、まあ、これらはそれ自体では無意味な名前です。何でも使用できます。ただし、慣例では1文字の大文字の値が提案されており、Tはジェネリックメソッドによく使用され、Eはクラスに使用されます....

于 2013-11-05T18:19:06.017 に答える