๋ณธ๋ฌธ ๋ฐ”๋กœ๊ฐ€๊ธฐ
Today I Learned(TIL)/Java

Java ๊ธฐ๋ณธํŽธ ๊ฐ•์˜_๋‹คํ˜•์„ฑ1

by carrot0911 2024. 12. 2.

๋‹คํ˜•์„ฑ 1

 

๋‹คํ˜•์„ฑ ์‹œ์ž‘

๊ฐ์ฒด ์ง€ํ–ฅ ํ”„๋กœ๊ทธ๋ž˜๋ฐ์˜ ๋Œ€ํ‘œ์ ์ธ ํŠน์ง•์œผ๋กœ๋Š” ์บก์Šํ™”, ์ƒ์†, ๋‹คํ˜•์„ฑ์ด ์žˆ๋‹ค. ๊ทธ์ค‘์—์„œ ๋‹คํ˜•์„ฑ์€ ๊ฐ์ฒด ์ง€ํ–ฅ ํ”„๋กœ๊ทธ๋ž˜๋ฐ์˜ ๊ฝƒ์ด๋ผ ๋ถˆ๋ฆฐ๋‹ค.
์•ž์„œ ํ•™์Šตํ–ˆ๋˜ ์บก์Šํ™”๋‚˜ ์ƒ์†์€ ์ง๊ด€์ ์œผ๋กœ ์ดํ•ดํ•˜๊ธฐ ์‰ฝ๋‹ค. ๋ฐ˜๋ฉด์— ๋‹คํ˜•์„ฑ์€ ์ œ๋Œ€๋กœ ์ดํ•ดํ•˜๊ธฐ๋„ ์–ด๋ ต๊ณ , ์ž˜ ํ™œ์šฉํ•˜๊ธฐ๋Š” ๋” ์–ด๋ ต๋‹ค. ํ•˜์ง€๋งŒ ์ข‹์€ ๊ฐœ๋ฐœ์ž๊ฐ€ ๋˜๊ธฐ ์œ„ํ•ด์„œ๋Š” ๋‹คํ˜•์„ฑ์— ๋Œ€ํ•œ ์ดํ•ด๊ฐ€ ํ•„์ˆ˜๋‹ค.

๋‹คํ˜•์„ฑ(Polymorphism)์€ ์ด๋ฆ„ ๊ทธ๋Œ€๋กœ "๋‹ค์–‘ํ•œ ํ˜•ํƒœ", "์—ฌ๋Ÿฌ ํ˜•ํƒœ"๋ฅผ ๋œปํ•œ๋‹ค.
ํ”„๋กœ๊ทธ๋ž˜๋ฐ์—์„œ ๋‹คํ˜•์„ฑ์€ ํ•œ ๊ฐ์ฒด๊ฐ€ ์—ฌ๋Ÿฌ ํƒ€์ž…์˜ ๊ฐ์ฒด๋กœ ์ทจ๊ธ‰๋  ์ˆ˜ ์žˆ๋Š” ๋Šฅ๋ ฅ์„ ๋œปํ•œ๋‹ค. ๋ณดํ†ต ํ•˜๋‚˜์˜ ํƒ€์ž…์œผ๋กœ ๊ณ ์ •๋˜์–ด ์žˆ๋‹ค. ๊ทธ๋Ÿฐ๋ฐ ๋‹คํ˜•์„ฑ์„ ์‚ฌ์šฉํ•˜๋ฉด ํ•˜๋‚˜์˜ ๊ฐ์ฒด๊ฐ€ ๋‹ค๋ฅธ ํƒ€์ž…์œผ๋กœ ์‚ฌ์šฉ๋  ์ˆ˜ ์žˆ๋‹ค๋Š” ๋œป์ด๋‹ค. 

๋‹คํ˜•์„ฑ์„ ์ดํ•ดํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” 2๊ฐ€์ง€ ํ•ต์‹ฌ ์ด๋ก ์„ ์•Œ์•„์•ผ ํ•œ๋‹ค.

  • ๋‹คํ˜•์  ์ฐธ์กฐ
  • ๋ฉ”์„œ๋“œ ์˜ค๋ฒ„๋ผ์ด๋”ฉ

๋‹คํ˜•์  ์ฐธ์กฐ

๋”๋ณด๊ธฐ

Parent ํด๋ž˜์Šค

package poly;

public class Parent {

    public void parentMethod() {
        System.out.println("Parent.parentMethod");
    }
}

Child ํด๋ž˜์Šค

package poly;

public class Child extends Parent{

    public void childMethod() {
        System.out.println("Child.childMethod");
    }
}

Main ํด๋ž˜์Šค

package poly;

public class PolyMain {

    public static void main(String[] args) {
        // ๋ถ€๋ชจ ๋ณ€์ˆ˜๊ฐ€ ๋ถ€๋ชจ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ
        System.out.println("Parent -> Parent");
        Parent parent = new Parent();
        parent.parentMethod();

        // ์ž์‹ ๋ณ€์ˆ˜๊ฐ€ ์ž์‹ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ
        System.out.println("Child -> Child");
        Child child = new Child();
        child.parentMethod();
        child.childMethod();

        // ๋ถ€๋ชจ ๋ณ€์ˆ˜๊ฐ€ ์ž์‹ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ(๋‹คํ˜•์  ์ฐธ์กฐ)
        System.out.println("Parent -> Child");
        Parent poly = new Child();
        poly.parentMethod();

        //Child child1 = new Parent();  // ์ž์‹์€ ๋ถ€๋ชจ๋ฅผ ๋‹ด์„ ์ˆ˜ ์—†๋‹ค.

        //poly.childMethod();  // ์ž์‹์˜ ๊ธฐ๋Šฅ์€ ํ˜ธ์ถœํ•  ์ˆ˜ ์—†๋‹ค. ์ปดํŒŒ์ผ ์˜ค๋ฅ˜ ๋ฐœ์ƒ
    }
}

๋‹คํ˜•์  ์ฐธ์กฐ: ๋ถ€๋ชจ ํƒ€์ž…์˜ ๋ณ€์ˆ˜๊ฐ€ ์ž์‹ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ

Parent → Child : poly.parentMethod( )

  • ๋ถ€๋ชจ ํƒ€์ž…์˜ ๋ณ€์ˆ˜๊ฐ€ ์ž์‹ ์ธ์Šคํ„ด์Šค๋ฅผ ์ฐธ์กฐํ•œ๋‹ค.
  • Parent poly = new Child( )
  • Child ์ธ์Šคํ„ด์Šค๋ฅผ ๋งŒ๋“ค์—ˆ๋‹ค. ์ด ๊ฒฝ์šฐ ์ž์‹ ํƒ€์ž…์ธ Child๋ฅผ ์ƒ์„ฑํ–ˆ๊ธฐ ๋•Œ๋ฌธ์— ๋ฉ”๋ชจ๋ฆฌ ์ƒ์— Child์™€ Parent๊ฐ€ ๋ชจ๋‘ ์ƒ์„ฑ๋œ๋‹ค.
  • ์ƒ์„ฑ๋œ ์ฐธ์กฐ๊ฐ’์„ Parent ํƒ€์ž…์˜ ๋ณ€์ˆ˜์ธ poly์— ๋‹ด์•„๋‘”๋‹ค.

๋ถ€๋ชจ๋Š” ์ž์‹์„ ๋‹ด์„ ์ˆ˜ ์žˆ๋‹ค.

  • ๋ถ€๋ชจ ํƒ€์ž…์€ ์ž์‹ ํƒ€์ž…์„ ๋‹ด์„ ์ˆ˜ ์žˆ๋‹ค.
  • Parent poly๋Š” ๋ถ€๋ชจ ํƒ€์ž…์ด๋‹ค. new Child( )๋ฅผ ํ†ตํ•ด ์ƒ์„ฑ๋œ ๊ฒฐ๊ณผ๋Š” Child ํƒ€์ž…์ด๋‹ค.
    Java์—์„œ ๋ถ€๋ชจ ํƒ€์ž…์€ ์ž์‹ ํƒ€์ž…์„ ๋‹ด์„ ์ˆ˜ ์žˆ๋‹ค!
    • Parent poly = new Child( ) : ์„ฑ๊ณต
  • ๋ฐ˜๋Œ€๋กœ ์ž์‹ ํƒ€์ž…์€ ๋ถ€๋ชจ ํƒ€์ž…์„ ๋‹ด์„ ์ˆ˜ ์—†๋‹ค.
    • Child child1 = new Parent( ) : ์ปดํŒŒ์ผ ์˜ค๋ฅ˜ ๋ฐœ์ƒ

๋‹คํ˜•์  ์ฐธ์กฐ

  • Parent parent = new Parent( )
  • Child child = new Child( )

๊ทธ๋Ÿฐ๋ฐ Parent ํƒ€์ž…์˜ ๋ณ€์ˆ˜๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ž์‹ ์ธ Parent๋Š” ๋ฌผ๋ก ์ด๊ณ , ์ž์‹ ํƒ€์ž…๊นŒ์ง€ ์ฐธ์กฐํ•  ์ˆ˜ ์žˆ๋‹ค. ๋งŒ์•ฝ ์†์ž๊ฐ€ ์žˆ๋‹ค๋ฉด ์†์ž๋„ ๊ทธ ํ•˜์œ„ ํƒ€์ž…๋„ ์ฐธ์กฐํ•  ์ˆ˜ ์žˆ๋‹ค.

  • Parent poly = new Parent( )
  • Parent poly = new Child( )
  • Parent poly = new Grandson( ) : Child ํ•˜์œ„์— ์†์ž๊ฐ€ ์žˆ๋‹ค๋ฉด ๊ฐ€๋Šฅ

Java์—์„œ ๋ถ€๋ชจ ํƒ€์ž…์€ ์ž์‹ ์€ ๋ฌผ๋ก ์ด๊ณ , ์ž์‹ ์„ ๊ธฐ์ค€์œผ๋กœ ๋ชจ๋“  ์ž์‹ ํƒ€์ž…์„ ์ฐธ์กฐํ•  ์ˆ˜ ์žˆ๋‹ค.
์ด๊ฒƒ์ด ๋ฐ”๋กœ ๋‹ค์–‘ํ•œ ํ˜•ํƒœ๋ฅผ ์ฐธ์กฐํ•  ์ˆ˜ ์žˆ๋‹ค๊ณ  ํ•ด์„œ ๋‹คํ˜•์  ์ฐธ์กฐ๋ผ๊ณ  ํ•œ๋‹ค.

๋‹คํ˜•์„ฑ ์ฐธ์กฐ์˜ ํ•œ๊ณ„

Parent → Child : poly.childMethod( )

Parent poly = new Child( ) ์ด๋ ‡๊ฒŒ ์ž์‹์„ ์ฐธ์กฐํ•ญ ์ƒํ™ฉ์—์„œ poly๊ฐ€ ์ž์‹ ํƒ€์ž…์ธ Child์— ์žˆ๋Š” childMethod( )๋ฅผ ํ˜ธ์ถœํ•˜๋ฉด ์–ด๋–ป๊ฒŒ ๋ ๊นŒ?
poly.childMethod( )๋ฅผ ์‹คํ–‰ํ•˜๋ฉด ๋จผ์ € ์ฐธ์กฐ๊ฐ’์„ ํ†ตํ•ด ์ธ์Šคํ„ด์Šค๋ฅผ ์ฐพ๋Š”๋‹ค. ๊ทธ๋ฆฌ๊ณ  ๋‹ค์Œ์œผ๋กœ ์ธ์Šคํ„ด์Šค ์•ˆ์—์„œ ์‹คํ–‰ํ•  ํƒ€์ž…์„ ์ฐพ์•„์•ผ ํ•œ๋‹ค. ํ˜ธ์ถœ์ž์ธ poly๋Š” Parent ํƒ€์ž…์ด๋‹ค. ๋”ฐ๋ผ์„œ parent ํด๋ž˜์Šค๋ถ€ํ„ฐ ์‹œ์ž‘ํ•ด์„œ ํ•„์š”ํ•œ ๊ธฐ๋Šฅ์„ ์ฐพ๋Š”๋‹ค.
๊ทธ๋Ÿฐ๋ฐ ์ƒ์† ๊ด€๊ณ„๋Š” ๋ถ€๋ชจ ๋ฐฉํ–ฅ์œผ๋กœ ์ฐพ์•„ ์˜ฌ๋ผ๊ฐˆ ์ˆ˜ ์žˆ์ง€๋งŒ ์ž์‹ ๋ฐฉํ–ฅ์œผ๋กœ ์ฐพ์•„ ๋‚ด๋ ค๊ฐˆ ์ˆ˜๋Š” ์—†๋‹ค. Parent๋Š” ๋ถ€๋ชจ ํƒ€์ž…์ด๊ณ  ์ƒ์œ„์— ๋ถ€๋ชจ๊ฐ€ ์—†๋‹ค.
๋”ฐ๋ผ์„œ childMethod( )๋ฅผ ์ฐพ์„ ์ˆ˜ ์—†์œผ๋ฏ€๋กœ ์ปดํŒŒ์ผ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•œ๋‹ค.

childMethod( )๋ฅผ ํ˜ธ์ถœํ•˜๊ณ  ์‹ถ์œผ๋ฉด ์–ด๋–ป๊ฒŒ ํ•ด์•ผ ํ• ๊นŒ?
๋ฐ”๋กœ ์บ์ŠคํŒ…์ด ํ•„์š”ํ•˜๋‹ค.

๋‹คํ˜•์  ์ฐธ์กฐ์˜ ํ•ต์‹ฌ์€ ๋ถ€๋ชจ๋Š” ์ž์‹์„ ํ’ˆ์„ ์ˆ˜ ์žˆ๋‹ค๋Š” ๊ฒƒ์ด๋‹ค.

 

๋‹คํ˜•์„ฑ๊ณผ ์บ์ŠคํŒ…

Parent poly = new Child( )์™€ ๊ฐ™์ด ๋ถ€๋ชจ ํƒ€์ž…์˜ ๋ณ€์ˆ˜๋ฅผ ์‚ฌ์šฉํ•˜๊ฒŒ ๋˜๋ฉด poly.childMethod( )์™€ ๊ฐ™์ด ์ž์‹ ํƒ€์ž…์— ์žˆ๋Š” ๊ธฐ๋Šฅ์€ ํ˜ธ์ถœํ•  ์ˆ˜ ์—†๋‹ค.

๋”๋ณด๊ธฐ
package poly.basic;

import poly.Child;
import poly.Parent;

public class CastingMain1 {
    public static void main(String[] args) {
        // ๋ถ€๋ชจ ๋ณ€์ˆ˜๊ฐ€ ์ž์‹ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ(๋‹คํ˜•์  ์ฐธ์กฐ)
        Parent poly = new Child();
        // ๋‹จ ์ž์‹์˜ ๊ธฐ๋Šฅ์€ ํ˜ธ์ถœํ•  ์ˆ˜ ์—†๋‹ค. ์ปดํŒŒ์ผ ์˜ค๋ฅ˜ ๋ฐœ์ƒ
        //poly.childMethod();
        
        // ๋‹ค์šด์บ์ŠคํŒ…(๋ถ€๋ชจ ํƒ€์ž… -> ์ž์‹ ํƒ€์ž…)
        Child child = (Child) poly;
        child.childMethod();
    }
}
  • poly.childMethod( )๋ฅผ ํ˜ธ์ถœํ•˜๋ฉด ๋จผ์ € ์ฐธ์กฐ๊ฐ’์„ ์‚ฌ์šฉํ•ด์„œ ์ธ์Šคํ„ด์Šค๋ฅผ ์ฐพ๋Š”๋‹ค.
  • ์ธ์Šคํ„ด์Šค ์•ˆ์—์„œ ์‚ฌ์šฉํ•  ํƒ€์ž…์„ ์ฐพ์•„์•ผ ํ•œ๋‹ค. poly๋Š” Parent ํƒ€์ž…์ด๋‹ค.
  • Parent๋Š” ์ตœ์ƒ์œ„ ๋ถ€๋ชจ์ด๋‹ค. ์ƒ์† ๊ด€๊ณ„๋Š” ๋ถ€๋ชจ๋กœ๋งŒ ์ฐพ์•„์„œ ์˜ฌ๋ผ๊ฐˆ ์ˆ˜ ์žˆ๋‹ค. childMethod( )๋Š” ์ž์‹ ํƒ€์ž…์— ์žˆ์œผ๋ฏ€๋กœ ํ˜ธ์ถœํ•  ์ˆ˜ ์—†๋‹ค.
    ๋”ฐ๋ผ์„œ ์ปดํŒŒ์ผ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•œ๋‹ค.

๋‹ค์šด ์บ์ŠคํŒ…

ํ˜ธ์ถœํ•˜๋Š” ํƒ€์ž…์„ ์ž์‹์ธ Child ํƒ€์ž…์œผ๋กœ ๋ณ€๊ฒฝํ•˜๋ฉด ์ธ์Šคํ„ด์Šค์˜ Child์— ์žˆ๋Š” childMethod( )๋ฅผ ํ˜ธ์ถœํ•  ์ˆ˜ ์žˆ๋‹ค.

๋ถ€๋ชจ๋Š” ์ž์‹์„ ๋‹ด์„ ์ˆ˜ ์žˆ์ง€๋งŒ ์ž์‹์€ ๋ถ€๋ชจ๋ฅผ ๋‹ด์„ ์ˆ˜ ์—†๋‹ค.

  • Parent parent = new Child( ) : ๋ถ€๋ชจ๋Š” ์ž์‹์„ ๋‹ด์„ ์ˆ˜ ์žˆ๋‹ค.
  • Parent parent = child  // Child child ๋ณ€์ˆ˜: ๋ถ€๋ชจ๋Š” ์ž์‹์„ ๋‹ด์„ ์ˆ˜ ์žˆ๋‹ค.

๋ฐ˜๋ฉด์— ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ž์‹์€ ๋ถ€๋ชจ๋ฅผ ๋‹ด์„ ์ˆ˜ ์—†๋‹ค.

Child child = poly // Parent poly ๋ณ€์ˆ˜

๋ถ€๋ชจ ํƒ€์ž…์„ ์‚ฌ์šฉํ•˜๋Š” ๋ณ€์ˆ˜๋ฅผ ์ž์‹ ํƒ€์ž…์— ๋Œ€์ž…ํ•˜๋ ค๊ณ  ํ•˜๋ฉด ์ปดํŒŒ์ผ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•œ๋‹ค. ์ž์‹์€ ๋ถ€๋ชจ๋ฅผ ๋‹ด์„ ์ˆ˜ ์—†๋‹ค.
์ด๋•Œ๋Š” ๋‹ค์šด์บ์ŠคํŒ…์ด๋ผ๋Š” ๊ธฐ๋Šฅ์„ ์‚ฌ์šฉํ•ด์„œ ๋ถ€๋ชจ ํƒ€์ž…์„ ์ž ๊น ์ž์‹ ํƒ€์ž…์œผ๋กœ ๋ณ€๊ฒฝํ•˜๋ฉด ๋œ๋‹ค.

์ฐธ๊ณ ๋กœ ์บ์ŠคํŒ…์„ ํ•œ๋‹ค๊ณ  ํ•ด์„œ Parent poly์˜ ํƒ€์ž…์ด ๋ณ€ํ•˜๋Š” ๊ฒƒ์ด ์•„๋‹ˆ๋‹ค. ํ•ด๋‹น ์ฐธ์กฐ๊ฐ’์„ ๊บผ๋‚ด๊ณ  ๊บผ๋‚ธ ์ฐธ์กฐ๊ฐ’์ด Child ํƒ€์ž…์ด ๋˜๋Š” ๊ฒƒ์ด๋‹ค. ๋”ฐ๋ผ์„œ poly์˜ ํƒ€์ž…์€ Parent๋กœ ๊ธฐ์กด๊ณผ ๊ฐ™์ด ์œ ์ง€๋œ๋‹ค.

์บ์ŠคํŒ…

  • ์—…์บ์ŠคํŒ…(upcasting) : ๋ถ€๋ชจ ํƒ€์ž…์œผ๋กœ ๋ณ€๊ฒฝ
  • ๋‹ค์šด์บ์ŠคํŒ…(downcasting) : ์ž์‹ ํƒ€์ž…์œผ๋กœ ๋ณ€๊ฒฝ

 

์บ์ŠคํŒ…์˜ ์ข…๋ฅ˜

์ผ์‹œ์  ๋‹ค์šด ์บ์ŠคํŒ…

๋”๋ณด๊ธฐ
package poly.basic;

public class CastingMain2 {
    public static void main(String[] args) {
        // ๋ถ€๋ชจ ๋ณ€์ˆ˜๊ฐ€ ์ž์‹ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ(๋‹คํ˜•์  ์ฐธ์กฐ)
        Parent poly = new Child();
        // ๋‹จ ์ž์‹์˜ ๊ธฐ๋Šฅ์€ ํ˜ธ์ถœํ•  ์ˆ˜ ์—†๋‹ค. ์ปดํŒŒ์ผ ์˜ค๋ฅ˜ ๋ฐœ์ƒ
        //poly.childMethod();

        // ์ผ์‹œ์  ๋‹ค์šด์บ์ŠคํŒ… - ํ•ด๋‹น ๋ฉ”์„œ๋“œ๋ฅผ ํ˜ธ์ถœํ•˜๋Š” ์ˆœ๊ฐ„๋งŒ ๋‹ค์šด์บ์ŠคํŒ…
        ((Child) poly).childMethod();
    }
}

์บ์ŠคํŒ…์„ ํ•œ๋‹ค๊ณ  ํ•ด์„œ Parent poly์˜ ํƒ€์ž…์ด ๋ณ€ํ•˜๋Š” ๊ฒƒ์€ ์•„๋‹ˆ๋‹ค. ํ•ด๋‹น ์ฐธ์กฐ๊ฐ’์„ ๊บผ๋‚ด๊ณ  ๊บผ๋‚ธ ์ฐธ์กฐ๊ฐ’์ด Child ํƒ€์ž…์ด ๋˜๋Š” ๊ฒƒ์ด๋‹ค.
๋”ฐ๋ผ์„œ poly์˜ ํƒ€์ž…์€ Parent๋กœ ๊ทธ๋Œ€๋กœ ์œ ์ง€๋œ๋‹ค.

์ด๋ ‡๊ฒŒ ์ผ์‹œ์  ๋‹ค์šด์บ์ŠคํŒ…์„ ์‚ฌ์šฉํ•˜๋ฉด ๋ณ„๋„์˜ ๋ณ€์ˆ˜ ์—†์ด ์ธ์Šคํ„ด์Šค์˜ ์ž์‹ ํƒ€์ž…์˜ ๊ธฐ๋Šฅ์„ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค.

์—…์บ์ŠคํŒ…

๋”๋ณด๊ธฐ
package poly.basic;

// upcasting vs downcasting
public class CastingMain3 {

    public static void main(String[] args) {
        Child child = new Child();
        Parent parent1 = (Parent) child;  // ์—…์บ์ŠคํŒ…์€ ์ƒ๋žต ๊ฐ€๋Šฅ, ์ƒ๋žต ๊ถŒ์žฅ
        Parent parent2 = child;  // ์—…์บ์ŠคํŒ… ์ƒ๋žต

        parent1.parentMethod();
        parent2.parentMethod();
    }

}

์—…์บ์ŠคํŒ…์€ ์ƒ๋žตํ•  ์ˆ˜ ์žˆ๋‹ค. ๋‹ค์šด์บ์ŠคํŒ…์€ ์ƒ๋žตํ•  ์ˆ˜ ์—†๋‹ค. ์ฐธ๊ณ ๋กœ ์—…์บ์ŠคํŒ…์€ ๋งค์šฐ ์ž์ฃผ ์‚ฌ์šฉํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์ƒ๋žต์„ ๊ถŒ์žฅํ•œ๋‹ค.
Java์—์„œ ๋ถ€๋ชจ๋Š” ์ž์‹์„ ๋‹ด์„ ์ˆ˜ ์žˆ๋‹ค. ํ•˜์ง€๋งŒ ๊ทธ ๋ฐ˜๋Œ€๋Š” ์•ˆ๋œ๋‹ค. (๊ผญ ํ•„์š”ํ•˜๋‹ค๋ฉด ๋‹ค์šด์บ์ŠคํŒ…์„ ํ•ด์•ผ ํ•œ๋‹ค.)

์—…์บ์ŠคํŒ…์€ ์ƒ๋žตํ•ด๋„ ๋˜๊ณ , ๋‹ค์šด์บ์ŠคํŒ…์€ ์™œ ๊ฐœ๋ฐœ์ž๊ฐ€ ์ง์ ‘ ๋ช…์‹œ์ ์œผ๋กœ ์บ์ŠคํŒ…์„ ํ•ด์•ผ ํ• ๊นŒ?

 

๋‹ค์šด ์บ์ŠคํŒ…๊ณผ ์ฃผ์˜์ 

๋‹ค์šด์บ์ŠคํŒ…์„ ์ž˜๋ชปํ•˜๋ฉด ์‹ฌ๊ฐํ•œ ๋Ÿฐํƒ€์ž„ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•  ์ˆ˜ ์žˆ๋‹ค.

๋”๋ณด๊ธฐ
package poly.basic;

// ๋‹ค์šด์บ์ŠคํŒ…์„ ์ž๋™์œผ๋กœ ํ•˜์ง€ ์•Š๋Š” ์ด์œ 
public class CastingMain4 {

    public static void main(String[] args) {
        Parent parent1 = new Child();
        Child child1 = (Child) parent1;
        child1.childMethod();  // ๋ฌธ์ œ ์—†์Œ

        Parent parent2 = new Parent();
        Child child2 = (Child) parent2;  // ๋Ÿฐํƒ€์ž„ ์˜ค๋ฅ˜ - ClassCastException
        child2.childMethod();  // ์‹คํ–‰ ๋ถˆ๊ฐ€
    }
}

๋จผ์ € new Parent( )๋กœ ๋ถ€๋ชจ ํƒ€์ž…์œผ๋กœ ๊ฐ์ฒด๋ฅผ ์ƒ์„ฑํ•œ๋‹ค. ๋ฉ”๋ชจ๋ฆฌ ์ƒ์— ์ž์‹ ํƒ€์ž…์€ ์ „ํ˜€ ์กด์žฌํ•˜์ง€ ์•Š๋Š”๋‹ค.

Java์—์„œ๋Š” ์ด๋ ‡๊ฒŒ ์‚ฌ์šฉํ•  ์ˆ˜ ์—†๋Š” ํƒ€์ž…์œผ๋กœ ๋‹ค์šด์บ์ŠคํŒ…ํ•˜๋Š” ๊ฒฝ์šฐ์— ClassCastException์ด๋ผ๋Š” ์˜ˆ์™ธ๋ฅผ ๋ฐœ์ƒ์‹œํ‚จ๋‹ค. ์˜ˆ์™ธ๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด ๋‹ค์Œ ๋™์ž‘์ด ์‹คํ–‰๋˜์ง€ ์•Š๊ณ , ํ”„๋กœ๊ทธ๋žจ์ด ์ข…๋ฃŒ๋œ๋‹ค.
๋”ฐ๋ผ์„œ child2.childMethod( ) ์ฝ”๋“œ ์ž์ฒด๊ฐ€ ์‹คํ–‰๋˜์ง€ ์•Š๋Š”๋‹ค.

์—…์บ์ŠคํŒ…์ด ์•ˆ์ „ํ•˜๊ณ  ๋‹ค์šด์บ์ŠคํŒ…์ด ์œ„ํ—˜ํ•œ ์ด์œ 

์—…์บ์ŠคํŒ…์˜ ๊ฒฝ์šฐ ์ด๋Ÿฐ ๋ฌธ์ œ๊ฐ€ ์ ˆ๋Œ€๋กœ ๋ฐœ์ƒํ•˜์ง€ ์•Š๋Š”๋‹ค. ์™œ๋ƒํ•˜๋ฉด ๊ฐ์ฒด๋ฅผ ์ƒ์„ฑํ•˜๋ฉด ํ•ด๋‹น ํƒ€์ž…์˜ ์ƒ์œ„ ๋ถ€๋ชจ ํƒ€์ž…์€ ๋ชจ๋‘ ํ•จ๊ป˜ ์ƒ์„ฑ๋œ๋‹ค!
๋”ฐ๋ผ์„œ ์œ„๋กœ๋งŒ ํƒ€์ž…์„ ๋ณ€๊ฒฝํ•˜๋Š” ์—…์บ์ŠคํŒ…์€ ๋ฉ”๋ชจ๋ฆฌ ์ƒ์— ์ธ์Šคํ„ด์Šค๊ฐ€ ๋ชจ๋‘ ์กด์žฌํ•˜๊ธฐ ๋•Œ๋ฌธ์— ํ•ญ์ƒ ์•ˆ์ „ํ•˜๋‹ค. ๊ทธ๋ž˜์„œ ์บ์ŠคํŒ…์„ ์ƒ๋žตํ•  ์ˆ˜ ์žˆ๋‹ค.

๋ฐ˜๋ฉด์— ๋‹ค์šด์บ์ŠคํŒ…์˜ ๊ฒฝ์šฐ ์ธ์Šคํ„ด์Šค์— ์กด์žฌํ•˜์ง€ ์•Š๋Š” ํ•˜์œ„ ํƒ€์ž…์œผ๋กœ ์บ์ŠคํŒ…ํ•˜๋Š” ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•  ์ˆ˜ ์žˆ๋‹ค. ์™œ๋ƒ๋ผ๋ฉด ๊ฐ์ฒด๋ฅผ ์ƒ์„ฑํ•˜๋ฉด ๋ถ€๋ชจ ํƒ€์ž…์€ ๋ชจ๋‘ ํ•จ๊ป˜ ์ƒ์„ฑ๋˜์ง€๋งŒ ์ž์‹ ํƒ€์ž…์€ ์ƒ์„ฑ๋˜์ง€ ์•Š๋Š”๋‹ค.
๋”ฐ๋ผ์„œ ๊ฐœ๋ฐœ์ž๊ฐ€ ์ด๋Ÿฐ ๋ฌธ์ œ๋ฅผ ์ธ์ง€ํ•˜๊ณ  ์‚ฌ์šฉํ•ด์•ผ ํ•œ๋‹ค๋Š” ์˜๋ฏธ๋กœ ๋ช…์‹œ์ ์œผ๋กœ ์บ์ŠคํŒ…์„ ํ•ด์ฃผ์–ด์•ผ ํ•œ๋‹ค.

์ปดํŒŒ์ผ ์˜ค๋ฅ˜ vs ๋Ÿฐํƒ€์ž„ ์˜ค๋ฅ˜

์ปดํŒŒ์ผ ์˜ค๋ฅ˜๋Š” ๋ณ€์ˆ˜๋ช… ์˜คํƒ€, ์ž˜๋ชป๋œ ํด๋ž˜์Šค ์ด๋ฆ„ ์‚ฌ์šฉ ๋“ฑ Java ํ”„๋กœ๊ทธ๋žจ์„ ์‹คํ–‰ํ•˜๊ธฐ ์ „์— ๋ฐœ์ƒํ•˜๋Š” ์˜ค๋ฅ˜์ด๋‹ค. ์ด๋Ÿฐ ์˜ค๋ฅ˜๋Š” IDE์—์„œ ์ฆ‰์‹œ ํ™•์ธํ•  ์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์•ˆ์ „ํ•˜๊ณ  ์ข‹์€ ์˜ค๋ฅ˜์ด๋‹ค.
๋ฐ˜๋ฉด์— ๋Ÿฐํƒ€์ž„ ์˜ค๋ฅ˜๋Š” ์ด๋ฆ„ ๊ทธ๋Œ€๋กœ ํ”„๋กœ๊ทธ๋žจ์ด ์‹คํ–‰๋˜๊ณ  ์žˆ๋Š” ์‹œ์ ์— ๋ฐœ์ƒํ•˜๋Š” ์˜ค๋ฅ˜์ด๋‹ค. ๋Ÿฐํƒ€์ž„ ์˜ค๋ฅ˜๋Š” ๋งค์šฐ ์•ˆ ์ข‹์€ ์˜ค๋ฅ˜์ด๋‹ค. ์™œ๋ƒํ•˜๋ฉด ๋ณดํ†ต ๊ณ ๊ฐ์ด ํ•ด๋‹น ํ”„๋กœ๊ทธ๋žจ์„ ์‹คํ–‰ํ•˜๋Š” ๋„์ค‘์— ๋ฐœ์ƒํ•˜๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค.

 

instanceof

๋‹คํ˜•์„ฑ์—์„œ ์ฐธ์กฐํ˜• ๋ณ€์ˆ˜๋Š” ์ด๋ฆ„ ๊ทธ๋Œ€๋กœ ๋‹ค์–‘ํ•œ ์ž์‹์„ ๋Œ€์ƒ์œผ๋กœ ์ฐธ์กฐํ•  ์ˆ˜ ์žˆ๋‹ค.
๊ทธ๋Ÿฐ๋ฐ ์ฐธ์กฐํ•˜๋Š” ๋Œ€์ƒ์ด ๋‹ค์–‘ํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์–ด๋–ค ์ธ์Šคํ„ด์Šค๋ฅผ ์ฐธ์กฐํ•˜๊ณ  ์žˆ๋Š”์ง€ ํ™•์ธํ•˜๋ ค๋ฉด ์–ด๋–ป๊ฒŒ ํ•ด์•ผ ํ• ๊นŒ?

Parent parent1 = new Parent();
Parent parent2 = new Child();

Parent๋Š” ์ž์‹ ๊ณผ ๊ฐ™์€ Parent์˜ ์ธ์Šคํ„ด์Šค๋„ ์ฐธ์กฐํ•  ์ˆ˜ ์žˆ๊ณ , ์ž์‹ ํƒ€์ž…์ธ Child์˜ ์ธ์Šคํ„ด์Šค๋„ ์ฐธ์กฐํ•  ์ˆ˜ ์žˆ๋‹ค.
์ด๋•Œ parent1, parent2 ๋ณ€์ˆ˜๊ฐ€ ์ฐธ์กฐํ•˜๋Š” ์ธ์Šคํ„ด์Šค์˜ ํƒ€์ž…์„ ํ™•์ธํ•˜๊ณ  ์‹ถ๋‹ค๋ฉด instanceof ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ๋œ๋‹ค.

๋”๋ณด๊ธฐ
package poly.basic;

public class CastingMain5 {

    public static void main(String[] args) {
        Parent parent1 = new Parent();
        System.out.println("parent1 ํ˜ธ์ถœ");
        call(parent1);
        Parent parent2 = new Child();
        System.out.println("parent2 ํ˜ธ์ถœ");
        call(parent2);
    }

    private static void call(Parent parent) {
        parent.parentMethod();

        if (parent instanceof Child) {
            System.out.println("Child ์ธ์Šคํ„ด์Šค ๋งž์Œ.");
            Child child = (Child) parent;
            child.childMethod();
        } else {
            System.out.println("Child ์ธ์Šคํ„ด์Šค ์•„๋‹˜.");
        }
    }
}

 

๋‹คํ˜•์„ฑ๊ณผ ๋ฉ”์„œ๋“œ ์˜ค๋ฒ„๋ผ์ด๋”ฉ

๋‹คํ˜•์„ฑ์„ ์ด๋ฃจ๋Š” ๋˜ ํ•˜๋‚˜์˜ ์ค‘์š”ํ•œ ํ•ต์‹ฌ ์ด๋ก ์€ ๋ฐ”๋กœ ๋ฉ”์„œ๋“œ ์˜ค๋ฒ„๋ผ์ด๋”ฉ์ด๋‹ค.
๋ฉ”์„œ๋“œ ์˜ค๋ฒ„๋ผ์ด๋”ฉ์—์„œ ๊ผญ ๊ธฐ์–ตํ•ด์•ผ ํ•  ์ ์€ ์˜ค๋ฒ„๋ผ์ด๋”ฉ ๋œ ๋ฉ”์„œ๋“œ๊ฐ€ ํ•ญ์ƒ ์šฐ์„ ๊ถŒ์„ ๊ฐ€์ง„๋‹ค๋Š” ์ ์ด๋‹ค.
๊ทธ๋ž˜์„œ ์ด๋ฆ„๋„ ๊ธฐ์กด ๊ธฐ๋Šฅ์„ ๋ฎ์–ด ์ƒˆ๋กœ์šด ๊ธฐ๋Šฅ์„ ์žฌ์ •์˜ํ•œ๋‹ค๋Š” ๋œป์˜ ์˜ค๋ฒ„๋ผ์ด๋”ฉ์ด๋‹ค.

๋ฉ”์„œ๋“œ ์˜ค๋ฒ„๋ผ์ด๋”ฉ์˜ ์ง„์งœ ํž˜์€ ๋‹คํ˜•์„ฑ๊ณผ ํ•จ๊ป˜ ์‚ฌ์šฉํ•  ๋•Œ ๋‚˜ํƒ€๋‚œ๋‹ค.

  • Parent, Child ๋ชจ๋‘ value๋ผ๋Š” ๊ฐ™์€ ๋ฉค๋ฒ„ ๋ณ€์ˆ˜๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ๋‹ค.
    • ๋ฉค๋ฒ„ ๋ณ€์ˆ˜๋Š” ์˜ค๋ฒ„๋ผ์ด๋”ฉ ๋˜์ง€ ์•Š๋Š”๋‹ค.
  • Parent, Child ๋ชจ๋‘ method( )๋ผ๋Š” ๊ฐ™์€ ๋ฉ”์„œ๋“œ๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ๋‹ค. Child์—์„œ ๋ฉ”์„œ๋“œ๋ฅผ ์˜ค๋ฒ„๋ผ์ด๋”ฉํ–ˆ๋‹ค.
    • ๋ฉ”์„œ๋“œ๋Š” ์˜ค๋ฒ„๋ผ์ด๋”ฉ๋œ๋‹ค.
๋”๋ณด๊ธฐ

Parent ํด๋ž˜์Šค

package poly.overriding;

public class Parent {

    public String value = "parent";

    public void method() {
        System.out.println("Parent.method");
    }
}

 Child ํด๋ž˜์Šค

package poly.overriding;

public class Child extends Parent{

    public String value = "child";

    @Override
    public void method() {
        System.out.println("Child.method");
    }
}

Main ํด๋ž˜์Šค

package poly.overriding;

public class OverridingMain {

    public static void main(String[] args) {
        // ์ž์‹ ๋ณ€์ˆ˜๊ฐ€ ์ž์‹ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ
        Child child = new Child();
        System.out.println("Child -> Child");
        System.out.println("value = " + child.value);
        child.method();

        // ๋ถ€๋ชจ ๋ณ€์ˆ˜๊ฐ€ ๋ถ€๋ชจ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ
        Parent parent = new Parent();
        System.out.println("Parent -> Parent");
        System.out.println("value = " + parent.value);
        parent.method();

        // ๋ถ€๋ชจ ๋ณ€์ˆ˜๊ฐ€ ์ž์‹ ์ธ์Šคํ„ด์Šค ์ฐธ์กฐ (๋‹คํ˜•์  ์ฐธ์กฐ)
        Parent poly = new Child();
        System.out.println("Parent -> Parent");
        System.out.println("value = " + poly.value);  // ๋ณ€์ˆ˜๋Š” ์˜ค๋ฒ„๋ผ์ด๋”ฉ X
        poly.method();  // ๋ฉ”์„œ๋“œ๋Š” ์˜ค๋ฒ„๋ผ์ด๋”ฉ!
    }
}

Parent → Child

  • ์ด ๋ถ€๋ถ„์ด ์ค‘์š”ํ•˜๋‹ค.
  • poly ๋ณ€์ˆ˜๋Š” Parent ํƒ€์ž…์ด๋‹ค. ๋”ฐ๋ผ์„œ poly.value, poly.method( )๋ฅผ ํ˜ธ์ถœํ•˜๋ฉด ์ธ์Šคํ„ด์Šค์˜ Parent ํƒ€์ž…์—์„œ ๊ธฐ๋Šฅ์„ ์ฐพ์•„์„œ ์‹คํ–‰ํ•œ๋‹ค.
    • poly.value : Parent ํƒ€์ž…์— ์žˆ๋Š” value ๊ฐ’์„ ์ฝ๋Š”๋‹ค.
    • poly.method( ) : Parent ํƒ€์ž…์— ์žˆ๋Š” method( )๋ฅผ ์‹คํ–‰ํ•˜๋ ค๊ณ  ํ•œ๋‹ค. ๊ทธ๋Ÿฐ๋ฐ ํ•˜์œ„ ํƒ€์ž…์ธ Child.method( )๊ฐ€ ์˜ค๋ฒ„๋ผ์ด๋”ฉ ๋˜์–ด ์žˆ๋‹ค. ์˜ค๋ฒ„๋ผ์ด๋”ฉ ๋œ ๋ฉ”์„œ๋“œ๋Š” ํ•ญ์ƒ ์šฐ์„ ๊ถŒ์„ ๊ฐ€์ง„๋‹ค.
      ๋”ฐ๋ผ์„œ Parent.method( )๊ฐ€ ์•„๋‹ˆ๋ผ Child.method( )๊ฐ€ ์‹คํ–‰๋œ๋‹ค.

์˜ค๋ฒ„๋ผ์ด๋”ฉ ๋œ ๋ฉ”์„œ๋“œ๋Š” ํ•ญ์ƒ ์šฐ์„ ๊ถŒ์„ ๊ฐ€์ง„๋‹ค. ์˜ค๋ฒ„๋ผ์ด๋”ฉ์€ ๋ถ€๋ชจ ํƒ€์ž…์—์„œ ์ •์˜ํ•œ ๊ธฐ๋Šฅ์„ ์ž์‹ ํƒ€์ž…์—์„œ ์žฌ์ •์˜ํ•˜๋Š” ๊ฒƒ์ด๋‹ค.
๋งŒ์•ฝ ์ž์‹์—์„œ๋„ ์˜ค๋ฒ„๋ผ์ด๋”ฉ ํ•˜๊ณ  ์†์ž์—์„œ๋„ ๊ฐ™์€ ๋ฉ”์„œ๋“œ๋ฅผ ์˜ค๋ฒ„๋ผ์ด๋”ฉ์„ ํ•˜๋ฉด ์†์ž์˜ ์˜ค๋ฒ„๋ผ์ด๋”ฉ ๋ฉ”์„œ๋“œ๊ฐ€ ์šฐ์„ ๊ถŒ์„ ๊ฐ€์ง„๋‹ค. ๋” ํ•˜์œ„ ์ž์‹์˜ ์˜ค๋ฒ„๋ผ์ด๋”ฉ ๋œ ๋ฉ”์„œ๋“œ๊ฐ€ ์šฐ์„ ๊ถŒ์„ ๊ฐ€์ง€๋Š” ๊ฒƒ์ด๋‹ค.

๋‹คํ˜•์„ฑ์„ ์ด๋ฃจ๋Š” ํ•ต์‹ฌ ์ด๋ก ์ธ ๋‹คํ˜•์  ์ฐธ์กฐ์™€ ๋ฉ”์„œ๋“œ ์˜ค๋ฒ„๋ผ์ด๋”ฉ์— ๋Œ€ํ•ด ๋ฐฐ์› ๋‹ค.

  • ๋‹คํ˜•์  ์ฐธ์กฐ : ํ•˜๋‚˜์˜ ๋ณ€์ˆ˜ ํƒ€์ž…์œผ๋กœ ๋‹ค์–‘ํ•œ ์ž์‹ ์ธ์Šคํ„ด์Šค๋ฅผ ์ฐธ์กฐํ•  ์ˆ˜ ์žˆ๋Š” ๊ธฐ๋Šฅ์ด๋‹ค.
  • ๋ฉ”์„œ๋“œ ์˜ค๋ฒ„๋ผ์ด๋”ฉ : ๊ธฐ์กด ๊ธฐ๋Šฅ์„ ํ•˜์œ„ ํƒ€์ž…์—์„œ ์ƒˆ๋กœ์šด ๊ธฐ๋Šฅ์œผ๋กœ ์žฌ์ •์˜ํ•œ๋‹ค.