ํ‹ฐ์Šคํ† ๋ฆฌ ๋ทฐ

๐Ÿ“ฆ

์ž๋ฐ”๋ฅผ ๊ณต๋ถ€ํ•˜๋ฉด์„œ ์—ฌํƒœ ์ œ๋„ค๋ฆญ๊ณผ ์™€์ผ๋“œ์นด๋“œ๋ฅผ ๋Œ€์ถฉ ๊ฐ์œผ๋กœ๋งŒ ์žก๊ณ  ๋„˜์–ด๊ฐ€๋˜ ๊ฒƒ๋“ค์„ ์ด๋ฒˆ์— ๊ณต๋ถ€๋ฉด์„œ ๊ฐœ๋…์„ ํƒ„ํƒ„ํ•˜๊ฒŒ ๋‹ค์งˆ ์ˆ˜ ์žˆ์—ˆ๋‹ค.

๊ทธ๋Ÿฐ๋ฐ ์ œ๋„ค๋ฆญ ๋ฉ”์„œ๋“œ์™€ ์™€์ผ๋“œ์นด๋“œ ๋ฉ”์„œ๋“œ๋ฅผ ๊ฐ๊ฐ ์–ธ์ œ ์“ฐ๋Š” ๊ฒŒ ๊ฐ€์žฅ ๋ฒ ์ŠคํŠธ์ธ์ง€์— ๋Œ€ํ•œ ๊ถ๊ธˆ์ฆ์ด ์ƒ๊ฒผ๋‹ค.

์ด ๋‘ ๋ฐฉ์‹์˜ ์ฐจ์ด์™€ ์„ ํƒ ๊ธฐ์ค€์„ ๊น”๋”ํ•˜๊ฒŒ ์ •๋ฆฌํ•ด ๋ณด์•˜๋‹ค.


 

1. ์˜ˆ์ œ ์ฝ”๋“œ ์‚ดํŽด๋ณด๊ธฐ

์ƒ์œ„ ํด๋ž˜์Šค์ธ Fruit์™€ ์ด๋ฅผ ์ƒ์†๋ฐ›๋Š” Apple, Banana๊ฐ€ ์žˆ๊ณ , ๊ณผ์ผ์„ ๋‹ด๋Š” FruitBox ํด๋ž˜์Šค๊ฐ€ ์žˆ๋‹ค.

๊ทธ๋ฆฌ๊ณ  ์ด ์ƒ์ž์˜ ์ •๋ณด๋ฅผ ์ถœ๋ ฅํ•ด ์ฃผ๋Š” FruitPrinter ํด๋ž˜์Šค๋ฅผ ์ž‘์„ฑํ–ˆ๋‹ค.

public class FruitPrinter {

    // V1: ์ œ๋„ค๋ฆญ ๋ฉ”์„œ๋“œ ๋ฐฉ์‹
    public static <T extends Fruit> void printV1(FruitBox<T> box) {
        box.showInfo();
    }

    // V2: ์™€์ผ๋“œ์นด๋“œ ๋ฐฉ์‹
    public static void printV2(FruitBox<? extends Fruit> box) {
        box.showInfo();
    }
}

๊ทธ๋ฆฌ๊ณ  ์ด๋ฅผ ์‹คํ–‰ํ•˜๋Š” ํ…Œ์ŠคํŠธ ์ฝ”๋“œ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

public class FruitPrinterTest {

    public static void main(String[] args) {
        FruitBox<Apple> appleBox = new FruitBox<>();
        appleBox.in(new Apple("์‚ฌ๊ณผ", 1000));

        FruitBox<Banana> bananaBox = new FruitBox<>();
        bananaBox.in(new Banana("๋ฐ”๋‚˜๋‚˜", 2000));

        FruitPrinter.printV1(appleBox); // ์ œ๋„ค๋ฆญ ๋ฐฉ์‹
        FruitPrinter.printV2(appleBox); // ์™€์ผ๋“œ์นด๋“œ ๋ฐฉ์‹
    }
}

printV1๊ณผ printV2 ๋ชจ๋‘ ๋ฌธ์ œ์—†์ด ์ž˜ ์‹คํ–‰๋œ๋‹ค.

๊ทธ๋Ÿฐ๋ฐ ์ž๋ฐ”์—์„œ๋Š” ์ด์ฒ˜๋Ÿผ ๋‹จ์ˆœํžˆ ์ „๋‹ฌ๋ฐ›์€ ๊ฐ์ฒด๋ฅผ ์กฐํšŒ/์ถœ๋ ฅํ•˜๋Š” ์ƒํ™ฉ์—์„œ๋Š”

์™€์ผ๋“œ์นด๋“œ ๋ฐฉ์‹์ธ printV2๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ๋” ๊ถŒ์žฅ๋˜๊ณ  ํšจ์œจ์ ์ด๋‹ค. ์™œ ๊ทธ๋Ÿด๊นŒ?

 

2. ์™œ ์™€์ผ๋“œ์นด๋“œ๊ฐ€ ๋” ์„ ํ˜ธ๋ ๊นŒ?

๊ฒฐ๋ก ๋ถ€ํ„ฐ ๋งํ•˜๋ฉด “์ฝ”๋“œ์˜ ๊ฐ„๊ฒฐํ•จ๊ณผ ์ง๊ด€์„ฑ” ๋•Œ๋ฌธ์ด๋‹ค.

1) ์ œ๋„ค๋ฆญ ๋ฉ”์„œ๋“œ (printV1)

public static <T extends Fruit> void printV1(FruitBox<T> box)

์ œ๋„ค๋ฆญ ๋ฉ”์„œ๋“œ๋Š” ๋ฉ”์„œ๋“œ ๋ฆฌํ„ด ํƒ€์ž… ์•ž๋ถ€๋ถ„์— ์ด๋ผ๋Š” ํƒ€์ž… ๋งค๊ฐœ๋ณ€์ˆ˜ ์„ ์–ธ๋ถ€๋ฅผ ํ•„์ˆ˜๋กœ ์ ์–ด์ค˜์•ผ ํ•œ๋‹ค.

ํ•˜์ง€๋งŒ ์ด ๋ฉ”์„œ๋“œ๋Š” ์ „๋‹ฌ๋ฐ›์€ box ๋‚ด๋ถ€์˜ showInfo()๋งŒ ํ˜ธ์ถœํ•˜๊ณ  ๋๋‚œ๋‹ค.

์ฆ‰, ํƒ€์ž… T๋ฅผ ๋ฉ”์„œ๋“œ ๋‚ด๋ถ€์—์„œ ๋”ฐ๋กœ ๋ณ€์ˆ˜๋กœ ์„ ์–ธํ•˜๊ฑฐ๋‚˜ ๋ฆฌํ„ด๊ฐ’์œผ๋กœ ์žฌ์‚ฌ์šฉํ•  ์ผ์ด ์ „ํ˜€ ์—†๋‹ค.

๊ฒฐ๊ตญ ๋”ฑ ํ•œ ๋ฒˆ ์“ฐ๊ธฐ ์œ„ํ•ด ํƒ€์ž… ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ์„ ์–ธํ•˜๋Š” ๋ถˆํ•„์š”ํ•œ ๋ฒˆ๊ฑฐ๋กœ์›€(Boilerplate)์ด ์ƒ๊ธฐ๋Š” ์…ˆ์ด๋‹ค.

2) ์™€์ผ๋“œ์นด๋“œ ๋ฉ”์„œ๋“œ (printV2)

public static void printV2(FruitBox<? extends Fruit> box)

๋ฐ˜๋ฉด ์™€์ผ๋“œ์นด๋“œ๋Š” ํƒ€์ž… ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ๋ฉ”์„œ๋“œ ์„ ์–ธ๋ถ€์— ๋”ฐ๋กœ ์ •์˜ํ•  ํ•„์š”๊ฐ€ ์—†๋‹ค.

๋งค๊ฐœ๋ณ€์ˆ˜ ์œ„์น˜์— ๊ณง๋ฐ”๋กœ ? ๋ฅผ ๋„ฃ์–ด ์ž‘์„ฑํ•œ๋‹ค.

์ด ์ฝ”๋“œ๊ฐ€ ์˜๋ฏธํ•˜๋Š” ๋ฐ”๋Š” ์•„์ฃผ ์ง๊ด€์ ์ด๋‹ค.

“์ด ๋ฉ”์„œ๋“œ๋Š” ํŠน์ • ํƒ€์ž… T๊ฐ€ ๋ฌด์—‡์ธ์ง€ ๊ธฐ์–ตํ•  ํ•„์š” ์—†์ด Fruit๋ฅผ ์ƒ์†๋ฐ›์€ ๊ณผ์ผ์„ ๋‹ด์€ FruitBox์ด๊ธฐ๋งŒ ํ•˜๋ฉด ๋‹ค ๋ฐ›์•„์ค„๊ฒŒ!”

 

๊ฐ€๋…์„ฑ๋„ ์ข‹์•„์ง€๊ณ  ๋ฌธ๋ฒ•๋„ ํ›จ์”ฌ ๋‹จ์ˆœํ•ด์ง„๋‹ค.


3. ํ•ต์‹ฌ ์ •๋ฆฌ: ์–ธ์ œ ๋ฌด์—‡์„ ์จ์•ผ ํ• ๊นŒ?

๊ณต๋ถ€ํ•˜๋ฉด์„œ ์ •๋ฆฌํ•œ ๋‚˜๋งŒ์˜ ๊ธฐ์ค€์€ ์•„๋ž˜์™€ ๊ฐ™๋‹ค.

๐Ÿ“Œ ์™€์ผ๋“œ์นด๋“œ๋ฅผ ์จ์•ผ ํ•˜๋Š” ์ƒํ™ฉ

  • ๋‹จ์ˆœํžˆ ์ธ์ž๋กœ ๋„˜์–ด์˜จ ๊ฐ์ฒด๋ฅผ ์กฐํšŒํ•˜๊ฑฐ๋‚˜ ์‚ฌ์šฉ(์ฝ๊ธฐ)๋งŒ ํ•  ๋•Œ
    • ์˜ˆ: printV2์ฒ˜๋Ÿผ ๋‹จ์ˆœํžˆ box.showInfo()๋ฅผ ํ˜ธ์ถœํ•˜๋Š” ๊ฒฝ์šฐ
  • ํƒ€์ž… ๋งค๊ฐœ๋ณ€์ˆ˜ T๊ฐ€ ๋ฉ”์„œ๋“œ ๋‚ด๋ถ€๋‚˜ ๋ฆฌํ„ด ํƒ€์ž…์—์„œ ์žฌ์‚ฌ์šฉ๋  ํ•„์š”๊ฐ€ ์—†์„ ๋•Œ
  • ์ฝ”๋“œ๋ฅผ ์งง๊ณ  ์ง๊ด€์ ์œผ๋กœ ์œ ์ง€ํ•˜๊ณ  ์‹ถ์„ ๋•Œ

๐Ÿ“Œ ์ œ๋„ค๋ฆญ ๋ฉ”์„œ๋“œ๋ฅผ ์จ์•ผ ํ•˜๋Š” ์ƒํ™ฉ

  • ์—ฌ๋Ÿฌ ๋งค๊ฐœ๋ณ€์ˆ˜ ๊ฐ„์˜ ํƒ€์ž… ์—ฐ๊ณ„(๊ด€๊ณ„)๊ฐ€ ํ•„์š”ํ•  ๋•Œ
public static <T extends Fruit> void move(FruitBox<T> from, FruitBox<T> to)

์œ„ ์ฝ”๋“œ์ฒ˜๋Ÿผ from๊ณผ to๊ฐ€ ๋ฐ˜๋“œ์‹œ ๋™์ผํ•œ ๊ณผ์ผ ํƒ€์ž…์ด์–ด์•ผ ํ•  ๋•Œ๋Š” ์ œ๋„ค๋ฆญ ๋ฉ”์„œ๋“œ๋ฅผ ์จ์•ผ ํ•œ๋‹ค.

์™€์ผ๋“œ์นด๋“œ๋ฅผ ์“ฐ๋ฉด from์€ ์‚ฌ๊ณผ ์ƒ์ž, to๋Š” ๋ฐ”๋‚˜๋‚˜ ์ƒ์ž๊ฐ€ ๋  ์ˆ˜๋„ ์žˆ์–ด์„œ ํƒ€์ž… ์•ˆ์ „์„ฑ์ด ๊นจ์ง„๋‹ค.

  • ๋ฉ”์„œ๋“œ์˜ ๋ฐ˜ํ™˜ ํƒ€์ž…์ด ์ž…๋ ฅ ๋งค๊ฐœ๋ณ€์ˆ˜์˜ ํƒ€์ž…๊ณผ ์—ฐ๊ด€๋  ๋•Œ
public static <T extends Fruit> T getFirstFruit(FruitBox<T> box)

 

       ์œ„ ์ฝ”๋“œ์ฒ˜๋Ÿผ ์ƒ์ž์—์„œ ๊ณผ์ผ์„ ๊บผ๋‚ด์„œ ๊ทธ ๊ณผ์ผ์˜ ํƒ€์ž… ๊ทธ๋Œ€๋กœ ๋ฐ˜ํ™˜ํ•ด์•ผ ํ•œ๋‹ค๋ฉด T ์„ ์–ธ์ด ํ•„์ˆ˜์ ์ด๋‹ค.

 

 

๋งˆ๋ฌด๋ฆฌ

์ฒ˜์Œ์—” ์™€์ผ๋“œ์นด๋“œ๊ฐ€ ๋ฌธ๋ฒ•๋งŒ ๋” ๋Š˜์–ด๋‚œ ๋А๋‚Œ์ด์—ˆ๋Š”๋ฐ

ํƒ€์ž… ๋งค๊ฐœ๋ณ€์ˆ˜์˜ ์žฌ์‚ฌ์šฉ์„ฑ ์—ฌ๋ถ€์™€ ๋งค๊ฐœ๋ณ€์ˆ˜ ๊ฐ„์˜ ํƒ€์ž… ์ผ์น˜ ํ•„์š”์„ฑ์ด๋ผ๋Š” ๊ธฐ์ค€์„ ์„ธ์šฐ๊ณ  ๋‚˜๋‹ˆ ๋ช…ํ™•ํ•ด์กŒ๋‹ค!