학습목표
- 객체 구조(데이터)와 기능(연산)을 분리하여 설계하는 방법 이해
- 새로운 기능을 객체 구조 변경 없이 확장하는 법을 학습
- 타입별 다른 처리가 필요한 다형성 구조 만들기
- 복잡한 객체 그래프(트리/컴포지트) 순회 방법 이해
활용 예제
- 복잡한 Composite 구조에 다양한 기능을 붙여야 할 때
- 객체 타입별 서로 다른 로직을 실행해야 할 때
- 기존 객체 구조는 건드리기 어렵거나 변경 위험이 있을 때
- 데이터 구조는 공통인데 ‘결과물만 다른 연산’을 추가하고 싶을 때
- 통계 계산
- 보고서 생성
예제
더보기
도메인 예: 문서(Document) 안에 여러 요소(Element)가 있고, 요소마다 “렌더링 방식이 다르게 동작”해야 하는 상황
- 방문받는 객체(Element) 인터페이스
interface DocumentElement {
void accept(DocumentVisitor visitor);
}
- 구체 요소들 (Paragraph, Image…)
class Paragraph implements DocumentElement {
private String text;
public Paragraph(String text) {
this.text = text;
}
public String getText() {
return text;
}
@Override
public void accept(DocumentVisitor visitor) {
visitor.visit(this);
}
}
class Image implements DocumentElement {
private String url;
public Image(String url) {
this.url = url;
}
public String getUrl() {
return url;
}
@Override
public void accept(DocumentVisitor visitor) {
visitor.visit(this);
}
}
- Visitor 인터페이스
interface DocumentVisitor {
void visit(Paragraph paragraph);
void visit(Image image);
}
- HTML 렌더러 , 텍스트 추출기
class HtmlRenderVisitor implements DocumentVisitor {
@Override
public void visit(Paragraph paragraph) {
System.out.println("<p>" + paragraph.getText() + "</p>");
}
@Override
public void visit(Image image) {
System.out.println("<img src='" + image.getUrl() + "' />");
}
}
class TextExtractorVisitor implements DocumentVisitor {
@Override
public void visit(Paragraph paragraph) {
System.out.println(paragraph.getText());
}
@Override
public void visit(Image image) {
System.out.println("[Image: " + image.getUrl() + "]");
}
}
- 구현
public class Main {
public static void main(String[] args) {
List<DocumentElement> elements = List.of(
new Paragraph("Hello World"),
new Image("https://example.com/image.png")
);
DocumentVisitor htmlVisitor = new HtmlRenderVisitor();
DocumentVisitor textVisitor = new TextExtractorVisitor();
System.out.println("=== HTML Render ===");
elements.forEach(e -> e.accept(htmlVisitor));
System.out.println("\n=== Text Extract ===");
elements.forEach(e -> e.accept(textVisitor));
}
}
- Paragraph, Image는 둘 다 같이 쓰고 방문자 구현 클래스에 따라 HTML이나 text로 표현하는 방식
마무리
리포트 같은 곳에서 같은 값들을 가지고 여러가지 방식으로 표현할 때 사용하기 좋아 보입니다.
'Java > 패턴' 카테고리의 다른 글
| 파사드 패턴 ( Facade Pattern ) (0) | 2025.12.02 |
|---|---|
| 책임사슬 패턴 ( Chain of Resposibility Pattern) (0) | 2025.12.01 |
| 데코레이터 패턴 ( Decorator Pattern ) (0) | 2025.11.26 |
| 컴포지트 패턴 ( Composite Pattern ) (0) | 2025.11.25 |
| 브릿지 패턴 ( Bridge Pattern ) (0) | 2025.11.24 |