
자바에서 오버라이딩은 부모 클래스의 메서드를 자식 클래스에서 재정의하는 기능입니다. 그런데 오버라이딩된 메서드는 무조건 자식 클래스의 메서드가 실행되는데, 그 이유는 동적 바인딩(Dynamic Binding) 때문입니다.
동적 바인딩이란 컴파일 시점이 아니라 실행 시점에 실제 호출된 메서드가 결정되는 것을 말합니다. 즉, 어떤 메서드가 실행될지는 프로그램이 실제로 실행되는 동안, 참조 변수의 실제 인스턴스 타입에 따라 결정된다는 것입니다.
자바는 컴파일 시점과 실행 시점을 명확히 구분합니다. 각 시점에는 수행되는 작업은 다음과 같습니다.
즉, 컴파일 시점에서는 어떤 메서드를 호출할 수 있는지 제한되지만, 실제 메서드 실행은 인스턴스 타입에 따라 결정됩니다.
Child chile = new Child();와 같은 경우, 참조 타입과 인스턴스 타입이 동일하기 때문에 동적 바인딩이 발생하지 않습니다. 이 경우, 실행 시점에 호출된 메서드는 이미 컴파일 시점에 결정됩니다.
class Parent {
void show() {
System.out.println("Parent의 show()");
}
}
class Child extends Parent {
@Override
void show() {
System.out.printn("Child의 show()");
}
}
public class Main {
public static void main(String[] args) {
Parent parent1 = new Child(); //업캐스팅 (참조 타입: Parent, 인스턴스 타입: Child)
parent1.show();/ //실행 결과: "Child의 show()"
}
}
✔ 컴파일 시점에서는 참조 타입에 따라 메서드를 호출할 수 있습니다.
✔ 실행 시점에서는 실제 인스턴스 타입에 따라 오버라이딩된 메서드가 실행됩니다.
✔ 동적 바인딩(Dynamic Binding) 덕분에, 자식 클래스의 메서드는 무조건 실행됩니다.
✔ Parent 클래스에만 있는 메서드는 컴파일 시점에 호출되지만, 자식 클래스에서 오버라이딩한 메서드는 실행 시점에 결정되어 실행됩니다.
✔ 동적 바인딩이 발생하지 않는 경우, 참조 타입과 인스턴스 타입이 동일하면 실행 시점에 호출되는 메서드가 이미 컴파일 시점에 결정됩니다.