MVC Pattern vs. MVVC Pattern vs. MVP Pattern#
MVC, MVP, MVVM 아키텍처 패턴은 모두 관심사 분리(SoC) 원칙에 기반하며, 각기 다른 방식으로 UI 로직과 비즈니스 로직을 분리한다.
MVC (Model-View-Controller)#
▫ 구조#
구성 요소 | 역할 |
---|
Model | 데이터 저장/비즈니스 로직 처리 |
View | UI 표시 (사용자 입력 수신) |
Controller | 입력 처리 → Model 업데이트 → View 갱신 |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
| # Model: 데이터와 비즈니스 로직
class UserModel:
def get_user_data(self):
return {"name": "홍길동", "age": 30}
# View: 사용자 인터페이스
class UserView:
def show_user(self, user_data):
print(f"사용자 정보: {user_data}")
# Controller: Model과 View 사이의 중재자
class UserController:
def __init__(self, model, view):
self.model = model
self.view = view
def display_user(self):
user = self.model.get_user_data()
self.view.show_user(user)
|
▫ 데이터 흐름#
1
2
| 사용자 → View → Controller → Model
Model → Controller → View
|
- 특징: View가 Model 직접 참조 가능
- 장점: 구조 단순, 학습 곡선 낮음
- 단점: View-Model 강결합 → 대규모 프로젝트 시 복잡성 증가
▫ 사용 사례#
- 웹 프레임워크(Spring MVC, Ruby on Rails)
- 간단한 데스크톱 애플리케이션
MVP (Model-View-Presenter)#
▫ 구조#
구성 요소 | 역할 |
---|
Model | 데이터 및 비즈니스 로직 |
View | UI 표시 (수동적, Presenter에 이벤트 전달) |
Presenter | View-Model 중재, UI 로직 처리 |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
| # Model: 데이터와 비즈니스 로직
class UserModel:
def get_user_data(self):
return {"name": "홍길동", "age": 30}
# View: 사용자 인터페이스와 이벤트 처리
class UserView:
def __init__(self, presenter):
self.presenter = presenter
def show_user(self, user_data):
print(f"사용자 정보: {user_data}")
# Presenter: View와 Model 사이의 중재자
class UserPresenter:
def __init__(self, view, model):
self.view = view
self.model = model
def load_user(self):
user = self.model.get_user_data()
self.view.show_user(user)
|
▫ 데이터 흐름#
1
2
| 사용자 → View → Presenter ↔ Model
Model → Presenter → View
|
- 특징: View-Model 완전 분리
- 장점: 테스트 용이성 ↑ (Presenter 단독 테스트 가능)
- 단점: View-Presenter 1:1 관계 → 코드량 증가
▫ 사용 사례#
- Windows Forms, Android 앱
- 복잡한 UI 로직이 필요한 프로젝트
MVVM (Model-View-ViewModel)#
▫ 구조#
구성 요소 | 역할 |
---|
Model | 데이터 소스 관리 |
View | UI 및 데이터 바인딩 |
ViewModel | View 상태 추상화, 데이터 변환 |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
| # Model: 데이터와 비즈니스 로직
class UserModel:
def get_user_data(self):
return {"name": "홍길동", "age": 30}
# ViewModel: View를 위한 Model의 데이터 변환과 상태 관리
class UserViewModel:
def __init__(self, model):
self.model = model
self.user_data = None
def fetch_user(self):
self.user_data = self.model.get_user_data()
# 데이터 바인딩을 통해 View가 자동으로 업데이트됨
# View: 사용자 인터페이스
class UserView:
def __init__(self, view_model):
self.view_model = view_model
# 데이터 바인딩 설정
|
▫ 데이터 흐름#
1
2
| 사용자 → View → ViewModel ↔ Model
Model → ViewModel → View (자동 갱신)
|
- 특징: 데이터 바인딩으로 자동 동기화
- 장점: 재사용성 ↑, 양방향 데이터 흐름
- 단점: 초기 설정 복잡, 과도한 추상화 가능성
▫ 사용 사례#
- WPF, Angular, React, Vue.js
- 실시간 데이터 업데이트 필요 애플리케이션
패턴 비교#
특성 | MVC | MVVM | MVP |
---|
데이터 흐름 | Controller → Model ↔ View | ViewModel ↔ Model, View ↔ ViewModel | Presenter → Model, View ↔ Presenter |
View와 Model의 관계 | 직접 참조 가능 | 완전 분리 | 완전 분리 |
중간 계층의 역할 | Controller가 입력 처리 | ViewModel이 상태와 데이터 변환 관리 | Presenter가 View 상태와 이벤트 처리 |
테스트 용이성 | 보통 | 좋음 | 매우 좋음 |
코드 복잡도 | 낮음 | 높음 | 중간 |
주요 사용처 | 웹 애플리케이션 | 데스크톱/모바일 앱 | 복잡한 UI 애플리케이션 |
데이터 바인딩 | 수동 | 자동 | 수동 |
UI 의존성 | 높음 | 낮음 | 매우 낮음 |
패턴 선택 가이드#
- MVC: 빠른 프로토타이핑, 간단한 웹 앱
- MVP: Android 앱, UI 테스트 강조 환경
- MVVM: 복잡한 데이터 플로우, 재사용성 요구 시
참고 및 출처#