Java ジェネリック (Generics) は、JDK5 で導入された新機能で、クラスとインターフェイスを定義するときに型パラメーター (Type Parameter) を使用できるようにします。宣言された型パラメーターは、使用時に特定の型に置き換えられます。現在、ジェネリックスの最も重要なアプリケーションは、Map と List が使用される JDK5 の新しいコレクション クラス フレームワークにあります。利点は自明ですが、より多くのクラスを水平に拡張できます。ジェネリック クラスを使用する場合、コードの目的を明確にする必要があり、型を使用できないためです。
最も基本的なジェネリック クラス
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e1;
/**
* 最も基本的なジェネリック クラス。型は自分で定義します
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス Point<T> {
プライベート T 変数。
public T getVar() {
変数を返します。
}
public void setVar(T var) {
this.var = var;
}
}
パッケージ com.garinzhang.javabase.generic.e1;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Point<String> p = 新しい Point<String> ();
p.setVar("コーダー");
System.out.println(p.getVar());
}
}
複数のジェネリック型
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e2;
/**
* 複数の汎用タイプ。一般に、S、R など、T に近い文字を使用するのが最適です。
* @著者ガリン・チャン
*
* @param <T>
* @param<S>
*/
パブリック クラス Notepad<T, S> {
秘密 T キー。
プライベート S 値。
public T getKey() {
this.key を返します。
}
public S getValue() {
this.value を返します。
}
public void setKey(T key) {
this.key = キー;
}
public void setValue(S 値) {
this.value = 値;
}
}
パッケージ com.garinzhang.javabase.generic.e2;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Notepad<String, Integer> p = new Notepad<String, Integer> ();
p.setKey("コーダー");
p.setValue(99999);
System.out.println("key: " + p.getKey());
System.out.println("値: " + p.getValue());
}
}
メソッドパラメータにワイルドカード「?」を使用する
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e3;
/**
* この例の鍵は main メソッドにあります
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス Info<T> {
秘密 T キー。
public T getKey() {
this.key を返します。
}
public void setKey(T key) {
this.key = キー;
}
@オーバーライド
public String toString() {
this.key.toString() を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e3;
/**
* メソッドパラメータでワイルドカードを使用する
* @著者ガリン・チャン
*
*/
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Info<String> i = 新しい Info<String>();
i.setKey("コーダー");
楽しい(i);
Info<Integer> j = 新しい Info<Integer>();
j.setKey(9999);
楽しい(j);
}
public static void fun(Info<?> temp) {
System.out.println("コンテンツ: " + temp);
}
}
上方変換が失敗する
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e4;
/**
* この例の鍵は main メソッドにあります
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス Info<T> {
秘密 T キー。
public T getKey() {
this.key を返します。
}
public void setKey(T key) {
this.key = キー;
}
@オーバーライド
public String toString() {
this.key.toString() を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e4;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Info<String> strEg = 新しい Info<String>();
Info<オブジェクト> objEg;
// コンパイル エラー "型が一致しません: Info<String> から Info<Object> に変換できません"
//アップキャストが失敗しました。文字列 -> オブジェクト
// objEg = strEg;
}
}
インターフェースでのジェネリックスの使用
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e5;
/**
* この例の鍵は main メソッドにあります
* @著者ガリン・チャン
*
* @param <T>
*/
インターフェース Info<T> {
public T getVar();
}
パッケージ com.garinzhang.javabase.generic.e5;
/**
* 汎用クラス
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス InfoImpl<T> は Info<T> を実装します {
プライベート T 変数。
public InfoImpl(T var) {
this.setVar(var);
}
public void setVar(T var) {
this.var = var;
}
public T getVar() {
this.var を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e5;
/**
* 非ジェネリッククラス
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス InfoImpl1 は Info<String> { を実装します。
プライベート文字列変数;
public InfoImpl1(String var) {
this.setVar(var);
}
public void setVar(String var) {
this.var = var;
}
public String getVar() {
this.var を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e5;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Info<String> strEg = new InfoImpl<String>("coder");
System.out.println("コンテンツ: " + strEg.getVar());
Info<String> strEg1 = new InfoImpl1("coder1");
System.out.println("コンテンツ: " + strEg1.getVar());
}
}
ワイルドカードとextendおよびsuperの使用
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e6;
/**
* この例の鍵は main メソッドにあります
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス Info<T> {
秘密 T キー。
public T getKey() {
this.key を返します。
}
public void setKey(T key) {
this.key = キー;
}
@オーバーライド
public String toString() {
this.key.toString() を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e6;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Info<String> strEg = 新しい Info<String>();
strEg.setKey("コーダー");
//コンパイル エラー "GenericExample 型のメソッド fun(Info<? extends Number>) は引数 (Info<String>) に適用できません"
// upTypeLimit(i);
// 整数型または数値型を使用します。
Info<Integer> intEg = new Info<Integer>();
intEg.setKey(9999);
upTypeLimit(intEg);
//コンパイル エラー「GenericExample 型のメソッド downTypeLimit(Info<? super String>) は引数 (Info<Integer>) に適用できません。」
// downTypeLimit(intEg);
// superを使用しているため、downTypeLimitはStringそのものとObjectしか受け取れません
// String の継承関係を確認しました。他のクラスは継承されず、Object のみが継承されます。
downTypeLimit(strEg);
Info<Object> objEg = new Info<Object>();
objEg.setKey(999);
downTypeLimit(objEg);
}
/**
* <? extends T> は型の上限を表し、パラメーター化された型が T または T のサブクラスである可能性があることを示します
* @param temp
*/
public static void upTypeLimit(Info<? extends Number> temp) {
System.out.println("コンテンツ: " + temp);
}
/**
* <? super T> は型の下限 (Java Core ではスーパー型修飾と呼ばれます) を表し、オブジェクトになるまでパラメータ化された型がこの型のスーパー型 (親型) であることを示します。
* この例では、String は Object からのみ継承するため、T は Object または String のみであることを意味します
* @param temp
*/
public static void downTypeLimit(Info<? super String> temp) {
System.out.println("コンテンツ: " + temp);
}
}
メソッド ジェネリックス、メソッド内の複数のジェネリックス
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e7;
/**
* メソッド ジェネリック、メソッド内の複数のジェネリック
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス 情報 {
/**
※形式:メソッド修飾 <カンマ区切りの型リスト> 戻り値の型 メソッド名(パラメータリスト)
* 例: public <T, S> T fun(T t, S s)
* @param t
* @param
* @戻る
*/
public <T, S> T fun(T t, S s) {
System.out.println(s.toString());
t を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e7;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
情報 info = 新しい Info();
String str = info.fun("coder", "print 2 番目の汎用パラメータ");
System.out.println(str);
int i = info.fun(30, "2 番目のパラメータを再度出力します");
System.out.println(i);
}
}
メソッドで渡される、またはメソッドで返されるジェネリック型は、メソッドの呼び出し時に設定されたパラメーターの型によって決まります。
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e8;
/**
* 延長します
* @著者ガリン・チャン
*
* @param <T>
*/
public class Info<T extends Number> {
プライベート T 変数。
public T getVar() {
this.var を返します。
}
public void setVar(T var) {
this.var = var;
}
@オーバーライド
public String toString() {
this.var.toString() を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e8;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Info<Integer> intEg = fun(30); // ここの型は Integer であると決定されています。
System.out.println(intEg.getVar());
}
/**
* メソッドで渡される、またはメソッドで返されるジェネリック型は、メソッド呼び出し時に設定されたパラメーターの型によって決まります。
* @param パラメータ
* @戻る
*/
public static <T extends Number> Info<T> fun(T param) {
Info<T> temp = 新しい Info<T>();
temp.setVar(param);
戻り温度;
}
}
メソッドで渡される 2 つのパラメータの型を一致させる
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e9;
/**
*メインを見る
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス Info<T> {
プライベート T 変数。
public T getVar() {
this.var を返します。
}
public void setVar(T var) {
this.var = var;
}
@オーバーライド
public String toString() {
this.var.toString() を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e9;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Info<String> i1 = 新しい Info<String>();
i1.setVar("こんにちは");
Info<String> i2 = 新しい Info<String>();
i2.setVar("コーダー");
Info<Integer> i3 = 新しい Info<Integer>();
i3.setVar(999);
追加(i1, i2);
//コンパイル エラー "GenericExample 型のメソッド add(Info<T>, Info<T>) は引数 (Info<String>, Info<Integer>) には適用できません"
// add(i1, i3);
}
/**
* メソッドで渡される 2 つのパラメータのタイプは一貫している必要があります
* @param パラメータ
* @戻る
*/
public static <T> void add(Info<T> i1, Info<T> i2) {
System.out.println(i1.getVar() + ":" + i2.getVar());
}
}
ジェネリックス、変数パラメーター。JavaScript の Arguments オブジェクトに似ています。
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e10;
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
整数 i[] = fun(1, 2, 3, 4, 5, 6);
fun2(i);
}
public static <T> T[] fun(T... arg) {
引数を返します。
}
public static <T> void fun2(T param[]) {
System.out.println("汎用配列: ");
for(T t : パラメータ) {
System.out.println(t + " ,");
}
}
}
ジェネリックネスト: ジェネリッククラスをパラメータとして使用し、戻り値の型に基づいて戻り値を決定します。
次のようにコードをコピーします。
パッケージ com.garinzhang.javabase.generic.e11;
/**
* 2 つのジェネリック型を受け入れます
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス Info<T, V> {
プライベート T 変数。
プライベート V 値。
public T getVar() {
this.var を返します。
}
public void setVar(T var) {
this.var = var;
}
public V getValue(){
this.value を返します。
}
public void setValue(V 値) {
this.value = 値;
}
@オーバーライド
public String toString() {
this.var.toString() を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e11;
/**
* 1 つのジェネリック型を受け入れます
* @著者ガリン・チャン
*
* @param <T>
*/
パブリック クラス Demo<S> {
プライベートS情報。
公開デモ(S情報) {
this.setInfo(情報);
}
public void setInfo(S info) {
this.info = 情報;
}
public S getInfo() {
this.info を返します。
}
}
パッケージ com.garinzhang.javabase.generic.e11;
java.util.Listをインポートします。
com.google.common.collect.Lists をインポートします。
パブリック クラス GenericExample {
/**
* @param 引数
*/
public static void main(String[] args) {
Demo<Info<String, Integer>> d;
Info<String, Integer> i;
i = 新しい Info<String, Integer>();
i.setVar("コーダー");
i.setValue(999);
d = 新しいデモ<Info<String,Integer>>(i);
System.out.println("コンテンツ: " + d.getInfo().getVar());
System.out.println("コンテンツ: " + d.getInfo().getValue());
System.out.println(query(1, 2, 3, 4, 5).toString()); // [1, 2, 3, 4, 5]
// 警告「タイプ セーフティ: Object&Comparable<?>&Serializable の汎用配列が varargs パラメータ用に作成されます」
System.out.println(query(1, 2, 3, "StringType").toString()); // [1, 2, 3, StringType]
System.out.println(query("I ", "am ", "a ", "coder").toString());// [I , am , a , coder]
List<String> list = Lists.newArrayList("I ", "am ", "a ", "coder");
System.out.println(list.toString()); // [私、私、コーダー]
}
/**
* 戻り値によってジェネリック型を決定します。このメソッドの戻り値の型はメソッドの定義によって自動的に生成されます。
* @param要素
* @戻る
*/
public static <E> List<E> query(E... 要素) {
// https://github.com/exitsoft/exit-web-framework/commit/1d2f1098a2a4b6abab175b793e2308aa8bd0ea16。
// com.google.common.collect.Lists をインポートします。
// <依存関係>
// <groupId>com.google.guava</groupId>
// <artifactId>グアバ</artifactId>
// <バージョン>16.0.1</バージョン>
// </依存関係>
Lists.newArrayList(elements) を返します。
}
}