このコード:(?1-のキャプチャ#リーダーを拡張)<? extends > Java構文
List<? extends Reader> weirdList;
weirdList.add(new BufferedReader(null));
は、メソッドが追加
のコンパイルエラーを持っているタイプ リストには適用されません 引数(BufferedReader)
なぜですか? BufferedReaderはリーダーを拡張するので、なぜそれが "一致"ではないのですか?
このコード:(?1-のキャプチャ#リーダーを拡張)<? extends > Java構文
List<? extends Reader> weirdList;
weirdList.add(new BufferedReader(null));
は、メソッドが追加
のコンパイルエラーを持っているタイプ リストには適用されません 引数(BufferedReader)
なぜですか? BufferedReaderはリーダーを拡張するので、なぜそれが "一致"ではないのですか?
:
List<? extends Reader> weirdList;
次の割り当てのすべてが有効です。
weirdList = new ArrayList<Reader>();
weirdList = new ArrayList<FileReader>();
weirdList = new ArrayList<BufferedReader>();
weirdList = new ArrayList<InputStreamReader>();
うまくいけば、これはあなたのコンパイルエラーについて説明します。 weirdList
にタイプArrayList<BufferedReader>
の値が入っていても、ArrayList<FileReader>
の値には意味がありません。 List<? extends Reader>
型の変数はいずれかの型の値を保持できるため、Javaではエラーが発生します。
Javaのジェネリックスは頭を悩ますことができません。 List<? extends Reader>
型は、さまざまな型を受け入れることができるように、メソッドの代入やパラメータ型に最も役立つと考えることができます。 「通常使用」の場合は、List<Reader>
やList<BufferedReader>
のような「ベア」ジェネリックの方が良いでしょう。
コンパイラは<? extends Reader>
を見たとき、それはそれがあるかReader
を拡張任意の型である可能性があることを前提としています。それはBufferedReader
と互換性がないもの、例えばStringReader
です。したがって、クラス定義のジェネリック型がadd
などのメソッドのパラメータに現れ、インスタンスのタイプが<? extends Something>
の場合、コンパイラは型の安全性の理由からそれを禁止する必要があります。この例では、はとなります。List<StringReader>
となるので、ここにBufferedReader
を追加することはできません。
List<? extends Reader> weirdList
は、いずれのタイプのReader
も格納する任意のタイプのList
を参照することができます。だから、weirdList2
を保存する必要があるために発生することが想定されていない(参照型が同じである)は、Javaを使用すると、weirdList1
にBufferedReader
を追加できるようになるならば、それはまた、あなたがweirdList2
にBufferedReader
を追加できるようにする必要があります
List<? extends Reader> weirdList1 = new ArrayList<BufferedReader>();
List<? extends Reader> weirdList2 = new ArrayList<FileReader>();
ことは可能ですのみFileReader
秒。あなたが与えた変数については
[Javaジェネリックスワイルドカード質問:リスト extends A>の可能な複製(http://stackoverflow.com/questions/5495383/java-generics-wildcard-question-list-extends-a) – yshavit
(FWIW、ここで何をしたいか'List <?extends Reader>'ではなく 'List'です。) –