「SJC-P ジェネリックス 型パラメータ」の版間の差分
ナビゲーションに移動
検索に移動
(ページの作成:「==SJC-P ジェネリックス 型パラメータ== ====型パラメータ(クラス)==== 以下のような箇所で使用できる *クラスの型 *インスタ…」) |
|||
20行目: | 20行目: | ||
GenericsTest4 me = new GenericsTest4(); | GenericsTest4 me = new GenericsTest4(); | ||
− | GenTypeTest | + | GenTypeTest<Date> gd = me.new GenTypeTest<Date>(); |
− | for (int i=0; i | + | for (int i=0; i<5; i++) { |
try { | try { | ||
Thread.sleep(500); | Thread.sleep(500); | ||
35行目: | 35行目: | ||
} | } | ||
} | } | ||
− | private class GenTypeTest | + | private class GenTypeTest<T> { // クラスの型 |
private T member; // インスタンス変数の型 | private T member; // インスタンス変数の型 | ||
private T[] members; // 配列の型 | private T[] members; // 配列の型 | ||
− | private List | + | private List<T> memList // コレクションに渡す |
− | = new ArrayList | + | = new ArrayList<T>(); |
private void addMember(T member) { // 引数 | private void addMember(T member) { // 引数 | ||
memList.add(member); | memList.add(member); | ||
55行目: | 55行目: | ||
} | } | ||
=====継承関係を指定===== | =====継承関係を指定===== | ||
− | * | + | * <T extends [Class or Interface]> で、指定クラス(インターフェース)の派生クラスであることを指定 |
− | * Clazz | + | * Clazz<? super [Class or Interface]> で、Clazzが、指定クラス(インターフェース)の基底クラスであることを指定 |
import java.util.ArrayList; | import java.util.ArrayList; | ||
import java.util.Collections; | import java.util.Collections; | ||
65行目: | 65行目: | ||
GenericsTest5 me = new GenericsTest5(); | GenericsTest5 me = new GenericsTest5(); | ||
− | CompareUtil | + | CompareUtil<Double> dc = me.new CompareUtil<Double>(); |
dc.addNum(1.23); | dc.addNum(1.23); | ||
dc.addNum(2.34); | dc.addNum(2.34); | ||
73行目: | 73行目: | ||
} | } | ||
// T型の基底クラス(T型を含む)に適応する Comparable を継承した T型 | // T型の基底クラス(T型を含む)に適応する Comparable を継承した T型 | ||
− | private class CompareUtil | + | private class CompareUtil<T extends Comparable<? super T>> { |
− | List | + | List<T> numList = new ArrayList<T>(); |
public void addNum(T num) { | public void addNum(T num) { | ||
numList.add(num); | numList.add(num); | ||
104行目: | 104行目: | ||
// メソッドで、ジェネリクス型を使う | // メソッドで、ジェネリクス型を使う | ||
// いろいろバージョンをオーバーロードしなくてもよい | // いろいろバージョンをオーバーロードしなくてもよい | ||
− | public static | + | public static <T extends Number> T log10(T num) { |
double ret = Math.log10(num.doubleValue()); | double ret = Math.log10(num.doubleValue()); | ||
return (T) new Double(ret); | return (T) new Double(ret); | ||
111行目: | 111行目: | ||
====拡張forループで使用する==== | ====拡張forループで使用する==== | ||
Messageクラスを保持するMessagesクラスを拡張forループに対応させる | Messageクラスを保持するMessagesクラスを拡張forループに対応させる | ||
− | *Iterable | + | *Iterable<Message>の実装 |
− | public class Messages implements Iterable | + | public class Messages implements Iterable<Message> { |
− | private List | + | private List<Message> messages; |
− | private List | + | private List<Message> getMessages(){ |
if (this.messages == null) { | if (this.messages == null) { | ||
− | this.messages = new ArrayList | + | this.messages = new ArrayList<Message>(); |
} | } | ||
return this.messages; | return this.messages; | ||
} | } | ||
− | public Iterator | + | public Iterator<Message> iterator() { |
return getMessages().iterator(); | return getMessages().iterator(); | ||
} | } |
2020年2月15日 (土) 08:05時点における版
目次
SJC-P ジェネリックス 型パラメータ
型パラメータ(クラス)
以下のような箇所で使用できる
- クラスの型
- インスタンス変数の型
- 配列の型
- コレクション等、他の型パラメータに渡す
- メソッド引数
- メソッド戻値
- キャスト
通常
import java.lang.reflect.Array; import java.util.ArrayList; import java.util.Date; import java.util.List; public class GenericsTest4 { public static void main(String[] args) { GenericsTest4 me = new GenericsTest4(); GenTypeTest<Date> gd = me.new GenTypeTest<Date>(); for (int i=0; i<5; i++) { try { Thread.sleep(500); } catch (InterruptedException e) { e.printStackTrace(); } Date d = new Date(); gd.addMember(d); } Date[] da = gd.getMemberAry(); for (Date d : da) { System.out.println(d.toString()); } } private class GenTypeTest<T> { // クラスの型 private T member; // インスタンス変数の型 private T[] members; // 配列の型 private List<T> memList // コレクションに渡す = new ArrayList<T>(); private void addMember(T member) { // 引数 memList.add(member); } private T[] getMemberAry() { // 戻値 // members = new T[memList.size()]; // NG インスタンスの生成 member = memList.get(0); members = (T[])Array.newInstance( // キャスト member.getClass(), memList.size()); memList.toArray(members); return members; } } }
継承関係を指定
- <T extends [Class or Interface]> で、指定クラス(インターフェース)の派生クラスであることを指定
- Clazz<? super [Class or Interface]> で、Clazzが、指定クラス(インターフェース)の基底クラスであることを指定
import java.util.ArrayList; import java.util.Collections; import java.util.List; public class GenericsTest5 { public static void main(String[] args) { GenericsTest5 me = new GenericsTest5(); CompareUtil<Double> dc = me.new CompareUtil<Double>(); dc.addNum(1.23); dc.addNum(2.34); dc.addNum(100.00); dc.addNum(-5.23); System.out.println(dc.getMax()); } // T型の基底クラス(T型を含む)に適応する Comparable を継承した T型 private class CompareUtil<T extends Comparable<? super T>> { List<T> numList = new ArrayList<T>(); public void addNum(T num) { numList.add(num); } public T getMax() { Collections.sort(numList); return numList.get(numList.size()-1); } } }
メソッドでジェネリックス型を利用する
- 戻値より前に書く必要がある
- ?は使えない(よく考えればわかる)
public class GenericsTest6 { public static void main(String[] args) { System.out.println(MathUtil.log10(365)); System.out.println(MathUtil.log10(0.56789)); // ボクシングと絡めて利用すると、挙動がややこしい // 上の例 MathUtil.log10(365) はOKだが、ここで同様にすると、エラー // オートボクシングにより、365 → Integer になり、戻値も Integer // アンボクシングにより、Integer → int で、Math.pow(double, double)に適合しなくなる // (Doubleにアンボクシングできない:java.lang.ClassCastException: java.lang.Double) System.out.println(Math.pow(10,MathUtil.log10(365.0))); System.out.println(Math.pow(10,MathUtil.log10(0.56789))); } } class MathUtil { // メソッドで、ジェネリクス型を使う // いろいろバージョンをオーバーロードしなくてもよい public static <T extends Number> T log10(T num) { double ret = Math.log10(num.doubleValue()); return (T) new Double(ret); } }
拡張forループで使用する
Messageクラスを保持するMessagesクラスを拡張forループに対応させる
- Iterable<Message>の実装
public class Messages implements Iterable<Message> { private List<Message> messages; private List<Message> getMessages(){ if (this.messages == null) { this.messages = new ArrayList<Message>(); } return this.messages; } public Iterator<Message> iterator() { return getMessages().iterator(); } public void add(int index, Message msg) { getMessages().add(index, msg); } public Message get(int index) { return getMessages().get(index); } }
© 2006 矢木浩人