2. SW complexity vs SW design
Decrease complexity
Top down approach
Separation of Concerns
Jintae Kim page 2
3. Practical SW design & Construction
Iterative
Incremental
Add, modify, delete
Jintae Kim page 3
4. Bad Smell
• Not modifiable
스파게티 코드 다수 존재
Feature enhance, bug fixing으로
인한 코드 수정 어려움
미흡한 영향평가로 new bug 등장
코드 수정 비용 증가
Jintae Kim page 4
5. Our goal is to design maintainable SW
• A good design is modifiable and flexible.
• A good design helps us to analyze side-effect when
modifying source code.
• A good design is to break down the complexity of Software.
• A good design comes from a good designer
Jintae Kim page 5
6. Requirements acquisition
• No Requirements specification, No design
• Requirements
Functional vs NonFunctional
Jintae Kim page 6
8. Prevent architecture erosion !!!
The well-designed SW does NOT become always good SW
Design Injection
Validation
Jintae Kim page 8
9. Make dummy functions
• Header file을 이용하여 함수 명 정의
함수 목적이 잘 드러나도록 기술
함수 목적을 코멘트로 기술
/***********************************************
* System : MOAKEY IM (Input Method)
* File : MOAIM.h
************************************************
/* MSG Callback Function */
LRESULT CALLBACK MOAWndProc (HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK DoCreateSIP (HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK DoPaintSIP (HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK DoLButtonUpSIP (HWND, UINT, WPARAM, LPARAM);
/* SIP 이미지를 drawing 한다. */
void drawingSIPImage();
/* SIP 상에서 Key가 눌렸다가 떼어졌을 때 처리*/
void onLButtonUp();
.....
.....
Jintae Kim page 9
10. Make the relations between functions
DoCreateSIP()
…
…
MOAWndProc() DoPaintSIP() drawingSIPImage()
…
…
DoLButtonUpSIP() onLButtonUp()
Jintae Kim page 10
12. Validate dummy structure
• 기본설계에 나타나는 구조와 소스코드의 구조 일치
소스상의 Call 구조의 예
• Call Depth (0.32) / function Complexity (1.69) 양호
소스코드를 이해하기에 적절하다 (이유: 실제 구현이 이뤄지지 않고 구조만 잡았기 때문)
• Unused functions 존재
기본설계 시 파악 치 못한 관계 존재하여 발생 (3개) (call graph 반영)
Jintae Kim page 12
13. Inject the relations of functions into source
code
• 함수의 파라미터, 반환 타입 • 함수 실행 조건 구현
구현
void drawingSIPImage(HWND p_hwnd) void drawingSIPImage(HWND p_hwnd)
{ {
#ifdef DEBUG_MOAIM
/* Pre Condition */
ASSERT(p_hwnd != NULL);
ASSERT(g_nSelSIPMode > -1);
ASSERT(g_nSelSIPMode < MAX_SIP);
/* SIP에해당되는이미지값이지정되어있어야한다.*/
ASSERT(sip_img_map[g_nSelHandlerMode][g_nSelDisplayMode
][g_nSelSIPMode][g_nSelInputMode].id > -1);
#endif // DEBUG_MOAIM
// // 현재모드에해당되는키보드이미지를화면에출력해준다.
현재모드에해당되는키보드이미지를화면에출력
해준다.
#ifdef DEBUG_MOAIM
/* Post Condition */
#endif // DEBUG_MOAIM
return;
return;
} }
Jintae Kim page 13
14. Validate the whole structure of dummy
functions
• 상세 설계의 구조가 소스코드 상에 잘 투영되었는지 검증
return / parameter type의 추가로 인한 구조 변경 여부 검증: 변경 사항 없음
Prototype 검증 시 발생된 추가/삭제된 함수의 구조 반영 여부 확인: 2개 함수가 구조에 반영
• Call Depth (0.67) / function Complexity (1.88) 양호
소스코드를 이해하기에 적절하다 (이유: 실제 구현이 이뤄지지 않고 구조만 잡았기 때문)
Prototype 검증때 보다는 call depth, function complexity 증가하였으나 그래도 적절한 수준
• Unused functions 존재
Prototype 검증시 파악된 3개 함수 중 2개만 반영
미반영 함수는 debug 메시지를 위한 함수였음
Jintae Kim page 14
16. DBC (Design By contract)
• 정직한 거래를 보장하는 최선의 해법 중 하나는 계약
• 계약
- 상대편과 자신의 권리와 책임을 정의
- 계약 위반 시 손해에 대해서도 정의
• DBC(계약에 의한 설계)
- 프로그램의 정확성을 보장하기 위해 소프트웨어 모듈의 권리와
책임을 문서화 하는데 초점
- 프로그램의 정확성: 스스로 자신이 하는 일이라고 주장하는
것보다 많거나 적지도 않게 딱 그 만큼만 하는 것
Jintae Kim page 16
17. DBC (Design By contract)
• 선행조건(precondition)
- 함수/메소드가 호출되기 위해 참이어야 하는 것
- 즉, 함수/메소드의 요구사항
- 선행조건이 위반된 경우(계약위반) 호출되어서는 안 된다.
- 제대로 된 데이터를 전달하는 것은 호출하는 쪽의 책임이다.
• 후행조건(postcondition)
- 함수/메소드가 자신이 할 것이라고 보장하는 것
- 즉, 함수/메소드가 완료되었을 때 세상의 상태
- 후행조건이 있다는 것은 곧 그것이 종국에는 종료될 것이라는 걸
암시.
- 무한반복 허용되지 않음
Jintae Kim page 17
18. DBC (Design By contract)
• 모듈불변식(module invariant)
- 호출자의 입장에서 볼 때는 이 조건이 언제나 참이라고 모듈이
보장
- 함수/메소드의 내부 처리 중에는 불변식이 참이 아닐 수도
있지만, 종료하고 호출자로 제어권이 반환되는 때에는 불변식이
참이 되어야 한다.
- 불변식에 관여하는 어떤 데이터 멤버에게도 모듈이 무제한적인
쓰기 접근권을 줄 수 없다는 것을 기억하라
추가 계약 내용
- 만약 호출자가 로틴의 모든 선행조건을 충족한다면, 해당 루틴은
종료 시 모든 후행조건과 불변식이 참이 될 것을 보증해야 한다.
Jintae Kim page 18