[디자인패턴] 템플릿 메서드(Template Method) 패턴이란?
Template Method 패턴은Behavioral design pattern이다.
템플릿이라는 말은 평소에도 많이 사용하기에 익숙하다. 템플릿 메서드 패턴이라는 말을 들으면 대충 무슨 역할을 하는지 알 수 있을 텐데 느끼는 것 그대로다! 템플릿 메서드 패턴은 상위 클래스에서 전체적인 알고리즘을 구현하고 다른 부분은 하위 클래스에서 구현할 수 있도록 하는 디자인 패턴이다. 알고리즘 세부 동작을 하위 클래스에서 구현할 수 있어 유연성과 확장성이 높고 코드 중복을 줄이고 유지보수를 쉽게 할 수 있다.
현대사에서 나온 모터를 사용해 구동하는 엘리베이터가 있다고 하자.
모터가 확장될 것에 대비해 클래스를 상위 클래스와 하위 클래스로 분류하고 확장에 용이하도록 만든 모습이다. 자랑스럽지 않은가?! 기대에 맞춰 회사는 현대사의 모터뿐만 아니라 LG사의 모터도 함께 취급하기로 했다.
엘리베이터는 사용할 모터에 맞춰 현대, LG 중 하나를 고르기만 하면 된다. 문제는 두 클래스 사이에 중복되는 코드가 많다는 것이다.
public void move(Direction direction) {
MotorStatus motorStatus = getMotorStatus();
if (motorStatus == MotorStatus.MOVING) return;
DoorStatus doorStatus = door.getDoorStatus();
if (doorStatus == DoorStatus.OPENED) door.close();
moveHyundaiMotor(direction);
setMotorStatus(MotorStatus.MOVING);
}
public void move(Direction direction) {
MotorStatus motorStatus = getMotorStatus();
if (motorStatus == MotorStatus.MOVING) return;
DoorStatus doorStatus = door.getDoorStatus();
if (doorStatus == DoorStatus.OPENED) door.close();
moveLGMotor(direction);
setMotorStatus(MotorStatus.MOVING);
}
위는 현대, 아래는 LG 모터를 사용하는 각자의 move 메서드 모습이다. move__Motor(direction); 을 제외한 모든 부분이 중복된다. 둘 사이에는 Motor라는 공통의 상위 클래스가 있다. 중복되는 부분을 모두 Motor에 넣고 중복되지 않는 부분만 하위 클래스에서 구현한다면 좋지 않을까?
public abstract class Motor {
protected Door door;
private MotorStatus motorStatus;
public Motor(Door door) { this.door = door; }
protected MotorStatus getMotorStatus() { return motorStatus; }
protected void setMotorStatus(MotorStatus motorStatus) { this.motorStatus = motorStatus; }
public void move(Direction direction) {
MotorStatus motorStatus = getMotorStatus();
if (motorStatus == MotorStatus.MOVING) return;
DoorStatus doorStatus = door.getDoorStatus();
if (doorStatus == DoorStatus.OPENED) door.close();
moveMotor(direction);
setMotorStatus(MotorStatus.MOVING);
}
private void moveMotor(Direction direction) { }
}
상위 클래스인 Motor의 모습이다. moveMotor는 비어있다. 하위 클래스에서 오버라이드하여 각자에 맞게 사용하면 된다.
public class HyundaiMotor extends Motor{
public HyundaiMotor(Door door) {
super(door);
}
protected void moveMotor() {
System.out.println("Hyundai Motor Initiated");
}
}
하위 클래스는 위처럼 move메서드를 전부 구현하지 않고 자신이 사용할 모터만 지정하는 moveMotor 메서드를 오버라이드한다. LG 모터도 마찬가지다.
상위 클래스는 abstract로 구현하여 하위 클래스의 메서드 구현을 강제할 수 있다.
이때 전반적인 골격·알고리즘을 제공하는 상위 클래스를 템플릿 메서드라고 부른다. 템플릿 메서드 내부에서 moveMotor처럼 비어있거나 기본 동작만 포함되어 하위 클래스가 선택적으로 오버라이드할 수 있는 메서드를 Hook(후크) 메서드라고 한다.
https://refactoring.guru/ko/design-patterns/template-method
템플릿 메서드 패턴
/ 디자인 패턴들 / 행동 패턴 템플릿 메서드 패턴 다음 이름으로도 불립니다: Template Method 의도 템플릿 메서드는 부모 클래스에서 알고리즘의 골격을 정의하지만, 해당 알고리즘의 구조를 변경하
refactoring.guru