[객체지향] 업캐스팅 다운캐스팅

2024. 6. 25. 10:24

✅ 업캐스팅(UpCasting)

  • 업캐스팅 → 상위 클래스로 형변환
    • 상위 클래스로 변수를 선언하고 하위 클래스의 생성자로 인스턴스를 생성하여 하위 클래스가 부모 클래스 타입으로 캐스팅되는 것이다
    • 업캐스팅은 캐스팅 연산자인 괄호를 생략할 수 있다
    • 업 캐스팅은 상위 클래스로 형 변환이기 때문에 실제 접근 가능한 변수나 메서드는 상위 클래스 변수와 메서드에 대해서 접근 가능하다 즉 속성과 메서드가 제한된다는 의미이다
    • 업 캐스팅 후 메서드 실행 시 하위 클래스에서 오버라이딩 메서드가 있다면 오버라이딩 된 메서드가 실행된다 → 자바의 모든 메서드는 가상 메서드(Virtual Method)
📌 가상 메서드 원리란?
가상 메서드 테이블에서 메서드에 대한 주소(address)를 가지고 있다 따라서 메서드 호출 시 메서드에 대한 주소를 이용하여 메서드를 호출한다. 다만 메서드가 재정의된 경우 가상 메서드 테이블에서메서드에 대한 주소를 재정의 된 메서드로 갱신한다.
// 업캐스팅 예시 코드
Customer customerLee = new VIPCustomer();

// VIPCustomer() 생성자에 의해 VIPCustomer 클래스의 모든 멤버 변수에 대한 메모리는 생성되었지만
// 변수 타입이 Customer이므로 실제 접근 가능한 변수나 메서드는 Customer의 변수와 메서드이다 

 

  • 상위 클래스 타입의 변수에 하위 클래스 변수 대입
// 업캐스팅 예시 코드
VIPCustomer vc = new VIPCustomer()
addCustomer(vc);

int addCustomer(Customer customer){
}
  • 하위 클래스는 상위 클래스의 타입을 내포하고 있으므로 상위 클래스로의 묵시적 형 변환이 가능하다
  • 상속관계에서 모든 하위 클래스는 상위 클래스로 형 변환(업캐스팅)이 되지만, 역은 성립하지 않는다.

✅  다운 캐스팅(DownCasting)

  • 다운 캐스팅
    • 업캐스팅된 클래스를 다시 원래의 타입으로 형 변환 하는 것을 의미한다
    • 하위 클래스로의 형 변환은 괄호를 이용하여 명시적으로 나타내야 한다
  • instanceof 연산자
    • 원래 인스턴스의 형이 맞는지 확인하기 위한 연산자이다
    • 반환 값으로 true, false를 반환한다
    • 다운 캐스팅을 하기 전에 변환이 가능한지 조사할 때 사용한다. 상속에서는 자식 클래스 타입인지, 인터페이스에서는 구현 클래스 타입인지를 확인할 때 사용한다
//instanceof 연산자를 이용한 다운캐스팅 예시 코드 

import java.util.ArrayList;

class Animal{
    public void move(){
        System.out.println("동물이 움직입니다");
    }
    public void eating(){

    }
}

class Human extends Animal {

    @Override
    public void move(){
        System.out.println("사람이 두 발로 걷습니다.");
    }
    public void readBook(){
        System.out.println("사람이 책을 읽습니다.");
    }
}

class Tiger extends Animal {

    @Override
    public void move(){
        System.out.println("호랑이가 네발로 뜁니다.");
    }
    public void hunting(){
        System.out.println("호랑이가 사냥을 합니다");
    }
}

class Eagle extends Animal {
    @Override
    public void move(){
        System.out.println("독수리가 하늘을 날아 다닙니다.");
    }
    public void flying(){
        System.out.println("독수리가 양날개를 쭉 펴고 날아다닙니다.");
    }
}

public class AnimalTest {

    public static void main(String[] args){

        Animal hAnimal = new Human();
        Animal tAnimal = new Tiger();
        Animal eAnimal = new Eagle();

        ArrayList<Animal> animalList = new ArrayList<>();
        animalList.add(hAnimal);
        animalList.add(tAnimal);
        animalList.add(eAnimal);

        for(Animal animal : animalList){
            animal.move();
        }
        testDownCasting(animalList);
    }

    public void testDownCasting(ArrayList<Animal> list){

        for(int i = 0; i < list.size(); i++){
            Animal animal = list.get(i);
            if(animal instanceof Human){
                Human human = (Human)animal;
                human.readBook();
            }
            else if(animal instanceof Tiger){
                Tiger tiger = (Tiger)animal;
                tiger.hunting();
            }
            else if(animal instanceof Eagle){
                Eagle eagle = (Eagle)animal;
                eagle.flying();
            }
            else {
                System.out.println("unsupported type");
            }

        }

    }

    public void moveAnimal(Animal animal){

        animal.move();
    }

}

'JAVA > 객체지향' 카테고리의 다른 글

[객체지향] 인터페이스  (0) 2024.07.08
[객체지향] 다형성  (0) 2024.06.26
[객체지향] Static  (0) 2024.06.26
[객체지향] this  (1) 2024.06.25
[객체지향] 클래스 상속  (0) 2024.06.24

BELATED ARTICLES

more