
다형성을 활용하면 역할과 구현을 분리해서, 클라이언트 코드의 변경 없이 구현 객체를 변경할 수 있다.
다음 관계에서 Driver가 클라이언트다.

앞서 설명한 자동차 예제를 코드로 구현해보자.
Driver : 운전자는 자동차(Car)의 역할에만 의존한다. 구현인 K3, Model3 자동차에 의존하지 않는다.Driver 클래스는 Car car 멤버 변수를 가진다. 따라서 Car 인터페이스를 참조한다.K3Car, Model3Car에 의존하지 않고, Car 인터페이스에만 의존한다.Driver 클래스 코드를 보면 Car 인터페이스만 사용하는 것을 확인할 수 있다.Car : 자동차의 역할이고 인터페이스이다. K3Car, Model3Car 클래스가 인터페이스를 구현한다.package poly.car1;
public interface Car {
void startEngine();
void offEngine();
void pressAccelerator();
}
package poly.car1;
public class K3Car implements Car {
@Override
public void startEngine() {
System.out.println("K3Car.startEngine");
}
@Override
public void offEngine() {
System.out.println("K3Car.offEngine");
}
@Override
public void pressAccelerator() {
System.out.println("K3Car.pressAccelerator");
}
}
package poly.car1;
public class Model3Car implements Car {
@Override
public void startEngine() {
System.out.println("Model3Car.startEngine");
}
@Override
public void offEngine() {
System.out.println("Model3Car.offEngine");
}
@Override
public void pressAccelerator() {
System.out.println("Model3Car.pressAccelerator");
}
}
package poly.car1;
public class Driver {
private Car car;
public void setCar(Car car) {
System.out.println("자동차를 설정합니다 : " + car);
this.car = car;
}
public void drive() {
System.out.println("자동차를 운전합니다.");
car.startEngine();
car.pressAccelerator();
car.offEngine();
}
}
Driver는 멤버 변수로 Car car를 가진다.setCar(Car car) : 멤버 변수에 자동차를 설정한다. 외부에서 누군가 이 메서드를 호출해주어야 Driver는 새로운 자동차를 참조하거나 변경할 수 있다.drive() : Car 인터페이스가 제공하는 기능들을 통해 자동차를 운전한다.package poly.car1;
public class CarMain1 {
public static void main(String[] args) {
Driver driver = new Driver();
// 차량 선택(K3)
K3Car k3Car = new K3Car();
driver.setCar(k3Car);
driver.drive();
// 차량 변경(K3 -> Model3)
Model3Car model3Car = new Model3Car();
driver.setCar(model3Car);
driver.drive();
}
}


Driver와 K3Car를 생성한다.driver.setCar(k3Car)를 호출해서 Driver의 Car car 필드가 K3Car의 인스턴스를 참조하도록 한다.driver.drive()를 호출하면 x001을 참조한다. car 필드가 Car 타입이므로 Car 타입을 찾아서 실행하지만 메서드 오버라이딩에 의해 K3Car의 기능이 호출된다.
Model3Car를 생성한다.driver.setCar(model3Car)를 호출해서 Driver의 Car car 필드가 Model3Car의 인스턴스를 참조하도록 변경한다.driver.drive()를 호출하면 x002를 참조한다. car 필드가 Car 타입이므로 Car 타입을 찾아서 실행하지만 메서드 오버라이딩에 의해 Model3Car의 기능이 호출된다.출처 : 김영한의 실전 자바 - 기본편
https://www.inflearn.com/course/김영한의-실전-자바-기본편/dashboard