JDK 1.5λΆν° λμ λ μ λ€λ¦(Generics)μ λν΄μ μμ보μ.
'μ λ€λ¦(Generic)μ μ¬μ©νλ©΄ λ€μν νμ μ μ¬μ©ν μ μλ€.' μ λλ‘λ§ μκ³ μμλλ° μ λλ‘ κ³΅λΆνλ €κ³ λ³΄λκΉ μκ°λ³΄λ€ μμ΄ λ§λ€. μ« λ§μ΄ λ§λ€...
κ·Έλμ μ΄λ² κΈμμλ μ λ€λ¦μ κΈ°λ² κ°λ μ λν΄μ μμλ³΄κ³ λ€μ κΈλ€μ ν΅ν΄ λ ꡬ체μ μΌλ‘ μμ보λ κ²μΌλ‘ νμ. (μ΄νν°λΈ μλ° 5μ₯μ μ λ€λ¦(μμ΄ν 26 ~ μμ΄ν 33) λ΄μ©κ³Ό μμΌλμΉ΄λ λ±μ λ΄μ©μ μΆκ°μ μΌλ‘ λ€λ£° μμ μ΄λ€.)
(μ΄νν°λΈ μλ° 5μ₯ μ λ€λ¦ ννΈλ₯Ό μ½μΌλ €λλ° μ΄ν΄κ° μ λμ§ μμμ μ λ€λ¦μ κΈ°λ³ΈλΆν° λΈλ‘κΉ νκ³ μλ μ€μ΄λ€...π )
1. μ λ€λ¦(Generic) κ°λ π§±
μ°λ¦¬λ μ λ€λ¦(Generics)μ κ·Έ μ΄λ ν κ°λ λ³΄λ€ μμ£Ό μ¬μ©νλ€.
public static void main(String[] args) {
ArrayList<Integer> numbers = new ArrayList<Integer>();
ArrayList<String> names = new ArrayList<String>();
}
// ArrayList.java
public class ArrayList<E> extends AbstractList<E>
implements List<E>, RandomAccess, Cloneable, java.io.Serializable
ArrayListμ κΊΎμ κ΄νΈ(< >)μμ ν΄λμ€ λ΄λΆμμ μ¬μ©ν λ°μ΄ν° νμ (Integer, String,..)μ μ§μ ν΄ μ£Όμλ€. μ΄κ²μ΄ μ λ€λ¦μ μ¬μ©ν κ²μ΄λ€.
μ λ€λ¦μ ν΄λμ€ λ΄λΆμμ μ¬μ©ν λ°μ΄ν° νμ μ μΈλΆμμ μ§μ νλ κΈ°λ²μ μλ―Ένλ€.
μ λ€λ¦μ λ€μν νμ μ κ°μ²΄λ€μ λ€λ£¨λ λ©μλλ 컬λ μ ν΄λμ€μ μ»΄νμΌ μμ νμ 체ν¬(compile-time type check)λ₯Ό ν΄μ£Όλ κΈ°λ₯μ μ 곡νλ€. κ°μ²΄μ νμ μ μ»΄νμΌ μμ 체ν¬νκΈ° λλ¬Έμ κ°μ²΄μ νμ μμ μ±μ λμ΄κ³ νλ³νμ λ²κ±°λ‘μμ΄ μ€μ΄λ λ€.
public static void main(String[] args) {
ArrayList<Integer> nums = new ArrayList<>();
// 1. νμ
μ μμ μ±μ μ 곡
nums.add(1);
// nums.add("1"); // μ»΄νμΌ μλ¬
// 2. νλ³νμ λ²κ±°λ‘μμ΄ μ€μ΄λ¬
Integer num = nums.get(0);
// Integer num1 = (Integer) nums.get(0);
}
π μ λ€λ¦μ μ₯μ
- νμ μμ μ±μ μ 곡
- νμ 체ν¬μ νλ³νμ μλ΅ν μ μμΌλ―λ‘ μ½λκ° κ°κ²°ν΄μ§λ€.
2. μ λ€λ¦ ν΄λμ€ π¨
μ λ€λ¦ νμ μ ν΄λμ€μ λ©μλμ μ μΈν μ μλ€. λ¨Όμ ν΄λμ€μ μ μΈνλ μ λ€λ¦ νμ μ λν΄μ μμ보μ.
π 1. μ λ€λ¦ ν΄λμ€ μ μΈ
λ€μκ³Ό κ°μ΄ κΈ°μ‘΄ ν΄λμ€ μμ '<T>'λ₯Ό λΆμ¬μ μ λ€λ¦ ν΄λμ€λ₯Ό λ§λ€ μ μλ€.
// κΈ°μ‘΄μ½λ
// μ λ€λ¦ ν΄λμ€ X
public class Box {
Object item;
void setItem(Object item) {
this.item = item;
}
Object getItem() {
return item;
}
}
// μ λ€λ¦ ν΄λμ€ O
public class Box<T> {
T item;
void setItem(T item) {
this.item = item;
}
T getItem() {
return item;
}
}
μ¬κΈ°μ Tλ νμ λ³μ(Type Variable)λΌκ³ νλ€. κΌ Tλ§μ μ¨μΌ νλ κ² μλλΌ E, K, V, N,... λ± λ€λ₯Έ κΈ°νΈλ₯Ό μ¬μ©ν΄λ λλ€. κΈ°νΈμ μ’ λ₯λ€λ§ λ€λ₯Ό λΏ 'μμμ μ°Έμ‘°ν νμ 'μ΄λΌλ κ²μ μλ―Ένλ€λ κ²μ λͺ¨λ κ°λ€.
νμ§λ§ μλμ κ°μ΄ μ묡μ μΈ κ·μΉμ΄ μ‘΄μ¬νλ―λ‘ μν©μ λ§κ² μλ―Ένλ λ¬Έμλ₯Ό μ νν΄μ μ¬μ©νλ κ²μ΄ μ’λ€.
νμ | μ€λͺ |
T | νμ (Type) |
E | μμ(Element) ex. ArrayList<E> |
K | ν€(Key) ex. Map<K, V> |
V | κ°(Value) |
μ λ€λ¦ ν΄λμ€λ₯Ό μ΄μ©νμ¬ κ°μ²΄λ₯Ό μμ±ν λλ μ°Έμ‘°λ³μμ μμ±μμ νμ T λμ μ μ¬μ©λ μ€μ νμ μ μ§μ ν΄ μ£Όλ©΄ λλ€.
public static void main(String[] args) {
// νμ
λ³μλ‘ Stringμ μ¬μ©ν κ²½μ°
Box<String> boxString = new Box<String>();
boxString.setItem("boxString");
String findBoxStringItem = boxString.getItem();
// νμ
λ³μλ‘ Integerλ₯Ό μ¬μ©ν κ²½μ°
Box<Integer> boxInteger = new Box<Integer>();
boxInteger.setItem(123);
Integer findBoxIntegerItem = boxInteger.getItem();
}
μ λ€λ¦μ΄ λμ λκΈ° μ΄μ μ μ½λμ νΈνμ μν΄, μ λ€λ¦ ν΄λμ€μΈλ°λ λ€μκ³Ό κ°μ΄ μμ μ λ°©μμΌλ‘ κ°μ²΄λ₯Ό μμ±νλ κ²μ΄ νμ©λλ€.
public static void main(String[] args) {
// μμ μ λ°©μμΌλ‘ κ°μ²΄λ₯Ό μμ±
Box boxPast = new Box();
boxPast.setItem("123");
Object findBoxPastItem = boxPast.getItem();
}
νμ§λ§, ν΄λΉ λ°©λ²μ λ¨μ§ μ λ€λ¦μ΄ λμ λκΈ° μ΄μ μ μ½λμ νΈνμ±μ μν κ²μ΄λ―λ‘ ν΄λΉ λ°©λ²μ μ¬μ©μ μ§μνλλ‘ νμ.
π 2. μ λ€λ¦ μ©μ΄
μ λ€λ¦μ λν΄μ μ΄λ μ λ κ°μ΄ μ‘νκ³ λ λ§μ κ°λ μ μκΈ° μν΄ μ§κΈ νμ΄λ°μ μ λ€λ¦μ μ©μ΄λ₯Ό νλ² μ§κ³ λμ΄κ°μ. μ©μ΄λ λ€μκ³Ό κ°λ€.
- Box<T>
μ λ€λ¦ ν΄λμ€
'Tμ Box' λλ 'T Box'λΌκ³ μ½λλ€. - T
νμ λ³μ λλ νμ 맀κ°λ³μ(Tλ νμ λ¬Έμ) - Box
μμ νμ (Raw Type)
- μ λ€λ¦ νμ
νΈμΆ
νμ 맀κ°λ³μ(T)μ νμ μ μ§μ νλ κ² - 맀κ°λ³μνλ νμ
(Parameterized Type)
μ§μ λ νμ (μμ κ·Έλ¦Όμμλ String)
μ©μ΄κ° μ’ κΈΈκΈ° λλ¬Έμ μ΄λ² κΈμμλ 'λμ λ νμ 'μ΄λΌκ³ μ¬μ©νμ.
π 3. μ λ€λ¦ μ ν
μ λ€λ¦ ν΄λμ€λ λ€μκ³Ό κ°μ 2κ°μ§ μν©μμ μ¬μ©ν μ μλ€.
π 1. staticλ©€λ²μ νμ λ³μ Tλ₯Ό μ¬μ©ν μ μλ€.
staticλ©€λ²λ λͺ¨λ κ°μ²΄μ λν΄ λμΌνκ² λμν΄μΌ νλ€.
Tλ μΈμ€ν΄μ€ λ³μλ‘ κ°μ£Όλκ³ , static λ©€λ²λ μΈμ€ν΄μ€ λ³μλ₯Ό μ°Έμ‘°ν μ μμΌλ―λ‘ static λ©€λ²μ νμ λ³μ Tλ₯Ό μ¬μ©ν μ μλ€.
class Box<T> {
static T item; // μλ¬
static int compare(T t1, T t2) {}; // μλ¬
}
π 2. μ λ€λ¦ νμ μ λ°°μ΄μ μμ±ν μ μλ€.
μ λ€λ¦ λ°°μ΄ νμ μ μ°Έμ‘°λ³μλ₯Ό μ μΈνλ κ²μ κ°λ₯νμ§λ§, 'new T[100]'κ³Ό κ°μ΄ λ°°μ΄μ μμ±νλ κ²μ μ λλ€.
class Box<T> {
// Tνμ
μ λ°°μ΄μ μν μ°Έμ‘° λ³μ
T[] itemArr; // OK
T[] toArray() {
// μ λ€λ¦ νμ
μ λ°°μ΄ μμ±
T[] tmpArr = new T[itemArr.length]; // μλ¬
return tmpArr;
}
}
μ λ€λ¦ λ°°μ΄μ μμ±ν μ μλ κ²μ newμ°μ°μ λλ¬Έμ΄λ€. new μ°μ°μλ μ»΄νμΌ μμ μ νμ Tκ° λ¬΄μμΈμ§ μ νν μμμΌ νλ€.
νμ§λ§ μμ μ½λμμ Box<T>ν΄λμ€λ₯Ό μ»΄νμΌνλ μμ μ Tκ° μ΄λ€ νμ μ΄ λ μ§ μ ν μ μ μλ€.
π 4. μ λ€λ¦ ν΄λμ€μ κ°μ²΄ μμ±κ³Ό μ¬μ©
Box<T>κ° λ€μκ³Ό κ°μ΄ μ μλμ΄ μλ€κ³ νμ.
class Box<T> {
ArrayList<T> list = new ArrayList<T>();
void add(T item) {
list.add(item);
}
T get(int i){
return list.get(i);
}
ArrayList<T> getList() {
return list;
}
int size() {
return list.size();
}
public String toString() {
return list.toString();
}
}
μ λ€λ¦ ν΄λμ€μ κ°μ²΄λ₯Ό μμ±νκ³ μ¬μ©ν λ λ€μμ κ·μΉμ μ£Όμν΄μ μμ± λ° μ¬μ©μ νλ©΄ λλ€. (Appleμ΄ Fruitμ μμμ΄λΌκ³ κ°μ νλ€.)
π 1. μ°Έμ‘°λ³μμ μμ±μμ λμ λ νμ (맀κ°λ³μνλ νμ )μ μΌμΉν΄μΌ νλ€.
public static void main(String[] args) {
// OK
Box<Apple> appleBox = new Box<Apple>();
// μλ¬
Box<Apple> appleBox = new Box<Grape>();
}
π 2. μΆμ μ΄ κ°λ₯ν νμ μλ΅ κ°λ₯(JDK 1.7λΆν°)
public static void main(String[] args) {
// OK
Box<Apple> appleBox = new Box<Apple>();
// OK // μλ΅ κ°λ₯
Box<Apple> appleBox = new Box<>();
}
π 3. λ€νμ±μ μ¬μ©νλ κ²½μ°
public static void main(String[] args) {
// μμ 1
Box<Apple> appleBox = new FruitBox<Apple>();
// μμ 2
Box<Fruit> fruitBox = new Box<Fruit>();
fruitBox.add(new Fruit());
fruitBox.add(new Apple());
}
π 5. μ νλ μ λ€λ¦ ν΄λμ€
λͺ¨λ μ’ λ₯μ νμ μ μ΄μ©νμ¬ νμ λ¬Έμλ₯Ό μ§μ ν μ μλ€.
λͺ¨λ μ’ λ₯μ νμ μΌλ‘ νμ λ¬Έμλ₯Ό μ§μ ν μ μλ κ²μ΄ μλ, μ νλ νμ μ μ’ λ₯λ‘ νμ λ¬Έμλ₯Ό μ§μ ν μ μλλ‘ νλ λ°©λ²μ μμ보λλ‘ νμ.
'extends'λ₯Ό μ¬μ©νλ©΄ νΉμ νμ κ³Ό νΉμ νμ μ μμλ€λ§ λμ ν μ μλλ‘ μ νν μ μλ€.
public class Fruit {
}
public class Apple extends Fruit{
}
public class FruitBox<T extends Fruit> {
ArrayList<T> list = new ArrayList<>();
}
public static void main(String[] args) {
FruitBox<Fruit> fruitBox = new FruitBox<>();
FruitBox<Apple> appleBox = new FruitBox<>();
}
μΈν°νμ΄μ€λ₯Ό ꡬνν΄μΌ νλ€λ μ μ½μ΄ νμνλ€λ©΄ μλμ κ°μ΄ μ¬μ©ν μ μλ€. (implementsκ° μλλΌ extendsλΌλ μ μ μ£Όμνμ.)
interface Eatable {}
class FruitBox<T extends Eatable> { ... }
Fruitμ μμμ΄λ©΄μ Eatable μΈν°νμ΄μ€λ ꡬνν΄μΌ νλ€λ©΄ '&'λ₯Ό μ΄μ©νμ¬ ννν μ μλ€.
class FruitBox<T extends Fruit & Eatable> { ... }
3. μμΌλμΉ΄λ π§
맀κ°λ³μμ κ³ΌμΌλ°μ€(FruitBox)λ₯Ό λμ νλ©΄ μ£Όμ€(Juice)λ₯Ό λ§λ€μ΄μ λ°ννλ JuicerλΌλ ν΄λμ€κ° μκ³ , μ΄ ν΄λμ€μ κ³ΌμΌμ μ£Όμ€λ‘ λ§λ€μ΄μ λ°ννλ makeJuice()λΌλ static λ©μλκ° μλ€κ³ νμ.
public class Juicer {
static Juice makeJuice(FruitBox<Fruit> box) {
String tmp = "";
for(Fruit f : box.getList())
tmp += f + " ";
return new Juice(tmp);
}
}
맀κ°λ³μλ‘ Fruitλ§ μ¬μ©νλ κ²μ΄ μλ λ€μν νμ μ μ¬μ©ν μ μλλ‘ μ λ€λ¦μ μ΄μ©νλ €κ³ νλ€. νμ§λ§ μλμ κ°μ λ¬Έμ κ° μλ€.
- Juicer ν΄λμ€λ μ λ€λ¦ ν΄λμ€κ° μλλ€.
- Juicer ν΄λμ€κ° μ λ€λ¦ ν΄λμ€λΌκ³ ν΄λ, static λ©μλμλ νμ 맀κ°λ³μ Tλ₯Ό 맀κ°λ³μμ μ¬μ©ν μ μλ€.
κ·Έλμ μ΄μ© μ μμ΄ μλμ κ°μ΄ μ¬λ¬ κ°μ§ νμ μ 맀κ°λ³μλ₯Ό κ°λ makeJuice()λ₯Ό λ§λ€μλ€κ³ νμ.
// λ©μλ μ€λ³΅ μ μ
public class Juicer {
static Juice makeJuice(FruitBox<Fruit> box) {
String tmp = "";
for(Fruit f : box.getList())
tmp += f + " ";
return new Juice(tmp);
}
static Juice makeJuice(FruitBox<Apple> box) {
String tmp = "";
for(Fruit f : box.getList())
tmp += f + " ";
return new Juice(tmp);
}
}
μ΄λ κ² μ€λ²λ‘λ©μ νλ©΄ μ»΄νμΌ μλ¬κ° λλ€. μ λ€λ¦ νμ μ΄ λ€λ₯΄λ€λ κ²λ§μΌλ‘λ μ€λ²λ‘λ©μ΄ μ±λ¦½νμ§ μκΈ° λλ¬Έμ΄λ€. μ λ€λ¦ νμ μ μ»΄νμΌλ¬κ° μ»΄νμΌν λλ§ μ¬μ©νκ³ μ κ±°νκΈ° λλ¬Έμ μμ λ λ©μλλ μ€λ²λ‘λ©μ΄ μλλΌ 'λ©μλ μ€λ³΅ μ μ'μ΄λ€.
μ΄λ° κ²½μ°μ μ¬μ©νκΈ° μν΄μ λ§λ€μ΄μ§ κ²μ΄ 'μμΌλμΉ΄λ'μ΄λ€. κΈ°νΈλ '?'μ΄κ³ , μμΌλμΉ΄λλ μ΄λ ν νμ λ κ°λ₯νλ€.
νμ§λ§ '?'μΌλ‘λ Object νμ κ³Ό λ€λ₯Ό κ² μμΌλ―λ‘ μΌλ°μ μΌλ‘ 'extends'μ 'super'λ₯Ό μ΄μ©νμ¬ μν(upper bound)κ³Ό νν(lower bound)μ λλ©΄μ μ¬μ©ν μ μλ€.
μμΌλμΉ΄λμμμ κ·μΉμ μλμ κ°λ€.
- <?>
νμ μ ν μμ
λͺ¨λ νμ μ΄ κ°λ₯
<? extends Object>μ λμΌ - <? extends T>
μμΌλμΉ΄λμ μν μ ν
Tμ κ·Έ μμλ€λ§ κ°λ₯ - <? super T>
μμΌλμΉ΄λμ νν μ ν
Tμ κ·Έ μ‘°μλ€λ§ κ°λ₯
π 1. <? extends T>
λ¨Όμ 'extends'λ₯Ό μ¬μ©νλ κ²½μ°λ₯Ό μ΄ν΄λ³΄μ. Juicer ν΄λμ€μ extendsλ₯Ό μ¬μ©νλ©΄ λ¬Έμ μ μν©μ ν΄κ²°ν μ μλ€.
public class Juicer {
static Juice makeJuice(FruitBox<? extends Fruit> box) {
String tmp = "";
for(Fruit f : box.getList())
tmp += f + " ";
return new Juice(tmp);
}
}
public static void main(String[] args) {
FruitBox<Fruit> fruitBox = new FruitBox<Fruit>();
FruitBox<Apple> appleBox = new FruitBox<Apple>();
System.out.println(Juicer.makeJuice(fruitBox));
System.out.println(Juicer.makeJuice(appleBox));
}
π 2. <? super T>
'super'λ₯Ό μ¬μ©ν κ²½μ°λ μ΄ν΄λ³΄μ. Fruitκ° μκ³ μμ ν΄λμ€λ‘ Appleκ³Ό Grapeκ° μλ€κ³ νμ.
public class Fruit {
String name;
int weight;
public Fruit(String name, int weight) {
this.name = name;
this.weight = weight;
}
}
public class Apple extends Fruit{
public Apple(String name, int weight) {
super(name, weight);
}
}
public class Grape extends Fruit{
public Grape(String name, int weight) {
super(name, weight);
}
}
Collections.sort()λ₯Ό μ΄μ©ν΄μ appleBoxμ grapeBoxμ λ΄κΈ΄ κ³ΌμΌμ 무κ²λ³λ‘ μ λ ¬νλ€κ³ νμ. Collections.sort()μ λ©μλ μ μΈλΆλ λ€μκ³Ό κ°λ€.
public static <T> void sort(List<T> list, Comparator<? super T> c)
첫 λ²μ§Έ 맀κ°λ³μλ μ λ ¬ν λμμ΄κ³ , λ λ²μ§Έ 맀κ°λ³μλ μ λ ¬ν λ°©λ²μ΄ μ μλ Comparatorμ΄λ€.
Collections.sort()κ° μμΌλμΉ΄λμ ννμ ν(<? super T>) μ¬μ©ν μ μλλ‘ νκ³ μμ§λ§, μ΄κ²μ μ΄μ©νμ§ μλλ€κ³ κ°μ ν΄ λ³΄μ.
κ·Έλ¬λ©΄ Collections.sort()λ₯Ό μ¬μ©ν λ νμ μ λͺ μνκ³ κ·Έμ ν΄λΉνλ Comparatorλ§ μ¬μ©ν΄μΌ ν κ²μ΄λ€.
public class AppleComp implements Comparator<Apple> {
@Override
public int compare(Apple o1, Apple o2) {
return Integer.compare(o1.weight, o2.weight);
}
}
public class GrapeComp implements Comparator<Grape> {
@Override
public int compare(Grape o1, Grape o2) {
return Integer.compare(o1.weight, o2.weight);
}
}
public static void main(String[] args) {
FruitBox<Apple> appleBox = new FruitBox<Apple>();
FruitBox<Grape> grapeBox = new FruitBox<Grape>();
appleBox.add(new Apple("GreenApple", 200));
appleBox.add(new Apple("GreenApple", 100));
grapeBox.add(new Grape("GreenApple", 200));
grapeBox.add(new Grape("GreenApple", 100));
Collections.sort(appleBox.getList(), new AppleComp());
Collections.sort(grapeBox.getList(), new GrapeComp());
}
AppleCompμ GrapeCompλ νμ λ§ λ€λ₯Ό λΏ μμ ν κ°μ μ½λμ΄λ€.
μ΄λ κ² μ¬μ©νλ€κ³ νλ©΄ μ½λ μ€λ³΅ λ¬Έμ λΏλ§ μλλΌ λ§μ½ μλ‘μ΄ Fruitμ μμμ΄ μκΈ΄λ€λ©΄ κ³μν΄μ μμ κ°μ μ½λλ₯Ό λ°λ³΅ν΄μ λ§λ€μ΄μΌ νλ€λ λ¬Έμ κ° μ‘΄μ¬νλ€.
μ΄λ₯Ό ν΄κ²°νκΈ° μν΄μ νμ λ§€κ° λ³μμ νν μ νμ μμΌλμΉ΄λ(<? super T>)λ₯Ό νμ©ν΄μΌ νλ€.
public class FruitComp implements Comparator<Fruit> {
@Override
public int compare(Fruit o1, Fruit o2) {
return Integer.compare(o1.weight, o2.weight);
}
}
public static void main(String[] args) {
FruitBox<Apple> appleBox = new FruitBox<Apple>();
FruitBox<Grape> grapeBox = new FruitBox<Grape>();
appleBox.add(new Apple("GreenApple", 200));
appleBox.add(new Apple("GreenApple", 100));
grapeBox.add(new Grape("GreenApple", 200));
grapeBox.add(new Grape("GreenApple", 100));
Collections.sort(appleBox.getList(), new FruitComp());
Collections.sort(grapeBox.getList(), new FruitComp());
}
μ΄λ κ² νλ©΄ AppleCompμ GrapeCompλ₯Ό λ°λ‘ μ¬μ©νλ κ²μ΄ μλ FruitCompλ§μ μ΄μ©ν΄μ μ λ ¬μ΄ κ°λ₯νλ€.
μ΄λ¬ν μ₯μ λλ¬Έμ Comparatorμλ νμ <? super T>κ° μ΅κ΄μ μΌλ‘ λ°λΌλΆκ² λλ€.
4. μ λ€λ¦ λ©μλ π©
μ λ€λ¦ νμ μ ν΄λμ€μ λ©μλμ μ μΈν μ μλ€κ³ νμλ€. μ§κΈκΉμ§λ ν΄λμ€μ μ μΈνλ μ λ€λ¦ νμ μ λν΄μ μμ보μκ³ , μ΄μ λΆν°λ λ©μλμ μ μΈνλ μ λ€λ¦ νμ μ λν΄μ μμ보μ.
λ©μλμ νμ λ³μκ° μλ€κ³ ν΄μ κ·Έκ²μ΄ μ λ€λ¦ λ©μλλ μλλ€.
public class FruitBox<T> {
// μ λ€λ¦ λ©μλ X
// νμ
λ³μλ‘ νμ
μ μ§μ ν λ©μλ O
public T addBox(T item){
...
}
}
μμ μ½λλ λ¨μ§ νμ λ³μλ‘ νμ μ μ§μ ν λ©μλλ€. μ λ€λ¦ λ©μλκ° μλλ€.
'μ λ€λ¦ λ©μλ'λ λ©μλμ μ μΈλΆμ μ λ€λ¦ νμ μ΄ μ μΈλ λ©μλλ₯Ό λ§νλ€. μ¦, λ©μλμ μ μΈλΆμ <T>κ° μμ΄μΌ νλ€.
static <T> void sort (List<T> list, Comparator<? super T> c)
μμ μ΄ν΄λ³Έ κ²μ²λΌ, Collections.sort()κ° λ°λ‘ μ λ€λ¦ λ©μλμ΄λ€. μ λ€λ¦ νμ μ μ μΈ μμΉλ λ°ν νμ λ°λ‘ μμ μμΉνλ€.
'μ λ€λ¦ ν΄λμ€μ μ μλ νμ 맀κ°λ³μ'μ 'μ λ€λ¦ λ©μλμ μ μλ νμ 맀κ°λ³μ'λ μ ν λ³κ°μ κ²μ΄λΌλ κ²μ μ£Όμνμ.
public class FruitBox<T> {
...
// 1λ² λ©μλ
// μ λ€λ¦ λ©μλ X
// νμ
λ³μλ‘ νμ
μ μ§μ ν λ©μλ O
// ν΄λμ€μ νμ
νλΌλ―Έν°λ₯Ό λ°μμ μ¬μ©νλ μΌλ° λ©μλ
public T addBox(T item){
...
}
// 2λ² λ©μλ
// μ λ€λ¦ λ©μλ O
// λ
립μ μΌλ‘ νμ
ν λΉ μ΄μλλ μ λ€λ¦ λ©μλ
static <T> void sort(List<T> list, Comparator<? super T> c) {
...
}
}
1λ² λ©μλλ μ λ€λ¦ λ©μλκ° μλκ³ , 2λ² λ©μλλ μ λ€λ¦ λ©μλμ΄λ€.
κ°κ°μ νΉμ§μ μλμ κ°λ€.
- μ λ€λ¦ λ©μλ X (1λ² λ©μλ)
ν΄λμ€μ μ λ€λ¦ <T>μμ μ€μ λ νμ μ λ°μμ λ°ν νμ μΌλ‘ μ¬μ©ν λΏμΈ μΌλ° λ©μλ - μ λ€λ¦ λ©μλ O (2λ² λ©μλ)
λ©μλμ <T> μ λ€λ¦μ μ€μ ν¨μΌλ‘μ¨ λμ μΌλ‘ νμ μ λ°μμ μ¬μ©ν μ μλ€.
λ 립μ μΌλ‘ μ΄μ© κ°λ₯νλ€.
μ λ€λ¦ ν΄λμ€ FruitBoxμ μ μΈλ νμ 맀κ°λ³μ Tμ μ λ€λ¦ λ©μλ sort()μ μ μΈλ νμ 맀κ°λ³μ Tλ νμ λ¬Έμλ§ κ°μ λΏ μλ‘ λ€λ₯Έ κ²μ΄λ€.
μ λ€λ¦ λ©μλλ₯Ό μ¬μ©νλ©΄ staticμ μ΄μ©ν μ μλ€λ κ²μ μ£Όλͺ©νμ. staticλ©€λ²μλ νμ 맀κ°λ³μλ₯Ό μ¬μ©ν μ μμ§λ§, μ΄μ²λΌ μ λ€λ¦ λ©μλμ μ λ€λ¦ νμ μ μ μΈνκ³ μ¬μ©νλ κ²μ κ°λ₯νλ€.
λ©μλμ μ μΈλ μ λ€λ¦ νμ μ μ§μ λ³μλ₯Ό μ μΈνλ κ²κ³Ό κ°λ€κ³ μκ°νλ©΄ μ΄ν΄νκΈ° μ¬μΈ κ²μ΄λ€. μ΄ νμ 맀κ°λ³μλ λ©μλ λ΄μμλ§ μ§μμ μΌλ‘ μ¬μ©λ κ²μ΄λ―λ‘ λ©μλμ staticμ λΆμΌ μ μλ€.
μμ μ΄ν΄λ³΄μλ makeJuice()λ₯Ό μ λ€λ¦ λ©μλλ‘ λ°κΎΈλ©΄ λ€μκ³Ό κ°λ€.
public class Juicer {
// κΈ°μ‘΄
static Juice makeJuice(FruitBox<? extends Fruit> box) {
String tmp = "";
for(Fruit f : box.getList())
tmp += f + " ";
return new Juice(tmp);
}
// μ λ€λ¦ λ©μλ μ μ©
static <T extends Fruit> Juice makeJuice(FruitBox<T> box) {
String tmp = "";
for(Fruit f : box.getList())
tmp += f + " ";
return new Juice(tmp);
}
}
λ©μλ νΈμΆμ νμ λ³μμ νμ μ λμ ν¨μΌλ‘μ¨ νΈμΆν μ μλ€.
public static void main(String[] args) {
FruitBox<Fruit> fruitBox = new FruitBox<Fruit>();
FruitBox<Apple> appleBox = new FruitBox<Apple>();
System.out.println(Juicer.<Fruit>makeJuice(fruitBox));
System.out.println(Juicer.<Apple>makeJuice(appleBox));
}
fruitBoxλ appleBoxμ μ μΈλΆλ₯Ό ν΅ν΄μ λμ λ νμ μ μ»΄νμΌλ¬κ° μΆμ ν μ μλ€. κ·Έλμ μλμ κ°μ΄ νμ μ μλ΅ν΄μ ννν μλ μλ€.
public static void main(String[] args) {
FruitBox<Fruit> fruitBox = new FruitBox<Fruit>();
FruitBox<Apple> appleBox = new FruitBox<Apple>();
System.out.println(Juicer.makeJuice(fruitBox));
System.out.println(Juicer.makeJuice(appleBox));
}
μ§κΈκΉμ§ μ λ€λ¦μ κΈ°λ³Έ κ°λ λ€μ μ΄ν΄λ³΄μλ€. κΈμ μλμμλ λ§νλ―μ΄ μ λ€λ¦μ λ΄μ©μ΄ μκ°λ³΄λ€ λ°©λνλ€. μ΄λ² κΈμ ν΅ν΄ κΈ°λ³Έ κ°λ μ μ μ΅νκ³ κ³μν΄μ μ λ€λ¦μ λ€λ₯Έ λ΄μ©λ€λ μ΄ν΄λ³Ό μ μλλ‘ νμ.
ν΄λΉ κΈμ
λ¨κΆμ± λμ 'μλ°μ μ μ',
Inpa λμ 'μλ° μ λ€λ¦(Generics) κ°λ & λ¬Έλ² μ 볡νκΈ°'
λ₯Ό μ°Έκ³ νμμ΅λλ€.
'π JAVA > μ£Όμ κ°λ ' μΉ΄ν κ³ λ¦¬μ λ€λ₯Έ κΈ
μ λ€λ¦(Generics) - 곡λ³(Covariant), λΆκ³΅λ³(Invariant), λ°κ³΅λ³(Contravariant) (0) | 2023.05.29 |
---|---|
νλ³ν(μΊμ€ν , Casting) - μ μΊμ€ν (Up-Casting), λ€μ΄μΊμ€ν (Down-Casting) (0) | 2023.05.24 |
λνΌ ν΄λμ€ (Wrapper Class) (0) | 2023.05.09 |
clone() (0) | 2023.04.07 |
μμ 볡μ¬(Shallow Copy) vs κΉμ 볡μ¬(Deep Copy) (0) | 2023.04.07 |