9장 - 의사코드 프로그래밍 프로세스
Edited by / 임수형 (sulogc)
9.1 클래스 및 루틴 개발 단계 요약
- 클래스 설계, 구체적인 루틴 열거 및 구현, 클래스 구현 검사를 반복하며 이뤄진다.
클래스 생성 단계
- 클래스에 대한 일반적인 설계를 작성한다. 클래스의 구체적인 책임을 정의, 클래스가 숨길 “비밀” 정의, 클래스 인터페이스가 추구할 추상화 정의. 루틴에 대한 직관적인 설계를 작성하는 데 필요한 만큼 과정을 반복.
- 클래스 내에 각 루틴을 구현한다.
- 루틴을 전체적으로 검토하고 테스트한다.
루틴을 작성하는 단계
주요 작업은 다음과 같다.
루틴을 작성하는 접근 방법으로 의사코드 프로그래밍 프로세스를 추천한다.
9.2 전문가를 위한 의사코드
의사코드는 알고리즘이나 루틴, 클래스, 프로그램이 어떻게 작동할지를 기술하는 자연어 문장과 같은 비형식적인 표기법을 가리킨다. 다음과 같은 지침이 있다.
- 구체적인 연산을 정확하게 기술하기 위해 자연어 문장과 같은 형태의 명령문을 사용
- 특정 프로그래밍 언어의 문법적인 요소를 피함.
- 목적에 초점을 맞춤.
- 의사코드로부터 코드를 거의 자동으로 생성할 수 있을 정도로 설계
장점은 다음과 같다.
- 의사 코드로 인해 낮은 수준의 설계 검토가 쉽다.
- 의사코드는 반복적인 개선을 지원한다.
- 의사코드는 코드에 비해 변경이 쉽다.
- 의사코드는 주석 작업을 최소화한다.
- 의사코드는 다른 설계 문서보다 유지보수가 쉽다.
9.3 PPP를 이용한 루틴 구현
루틴을 설계한다.
- 선행 조건을 검사한다.
- 루틴이 해결할 문제를 정의한다. 루틴이 해결할 문제를 당장 개발할 수 있을 정도로 자세히 기술한다. 루틴이 숨길 정보, 루틴 호출 전 입력 및 선행조건들, 루틴 호출 후 출력 및 후행조건들.
- 루틴의 이름을 짓는다. 모호하지 않고 명확하게.
- 루틴을 어떻게 테스트할 것인지 결정한다.
- 표준 라이브러리에서 사용할 수 있는 기능을 조사한다. 필요이상의 작업을 하지말고 재사용성을 높여라.
- 오류 처리에 대해 생각한다. 잘못된 입력 혹은 다른 루틴에서 반환된 유효하지 않은 값 등 모든 경우에 대해 고려
- 효율성에 대해서 생각한다. 보통은 효율성이 중요하지 않다. 나중에 루틴을 개선할 수 있ㅇ르 정도로 인터페이스의 추상화가 잘 되어 있는지와 루틴의 코드가 이해하기 쉬운지만 확인한다. 소수의 시스템의 경우 특정 루틴이 자원과 속도의 목표를 트레이드 오프 형태로 설계하여 조율하도록 한다. 이외의 경우, 루틴 설계 단계에서 효율성을 고민하는 건 시간낭비다.
- 알고리즘과 데이터형을 조사한다. 라이브러리에 없는 경우 알고리즘 책을 참고하자.
- 의사코드를 작성한다. 의사코드 작성은 일반적인 것부터 구체적인 것으로 진행한다.
- 데이터에 대해서 생각한다. 데이터 관리가 중요하다면, 논리적인 구조보다 데이터를 먼저 고민하는 것이 좋을 수 있다.
- 의사코드를 검사한다.
- 의사코드에서 몇 가지 아이디어를 내보고 가장 좋은 방법을 선택한다. 의사코드를 문서로 남겨둘 수 있을 만큼 간단해질 때까지 의사코드 개선이 필요하다.
루틴을 구현한다.
루틴 구현의 단계는 다음과 같다.
- 루틴의 선언부를 작성한다.
- 의사코드를 고수준의 주석으로 변환한다.
- 각 주석 아래에 코드를 채운다.
- 코드를 더 나눠야 하는지 검사한다. 명세가 상세하더라도 의사코드와 코드에서 실질적인 설계 작업이 필요하다.
코드를 검사한다.
- 머릿속에서 루틴의 오류를 검사한다. 루틴을 작게 유지하며, 정상적인 경로와 종결점, 예외 조건을 검사하는지 확인한다. 각 코드의 역할과 그것이 왜 필요한지 이해하도록하며, 그 코드가 왜 작동하는지 모른다면 아직 모르고 있을 뿐 나중에 아마 작동하지 않을 것이다.
- 루틴을 컴파일한다. “컴파일 한 판 더” 증후군에서 벗어나자.
- 코드를 디버거에서 한 단계씩 살펴본다.
- 코드를 테스트한다.
- 루틴에 있는 오류를 제거한다.
나머지를 정리한다.
루민의 인터페이스, 변수, 명령문과 논리적인 구조, 레이아웃, 문서화를 검사하고 설계 품질도 검사해야한다.
필요한 만큼 반복한다.
루틴의 품질이 좋지 않다면 의사코드 단계로 돌아간다.
9.4 PPP 대안
- 테스트 주도 개발 코드 작성전에 테스트 케이스를 먼저 작성
- 리펙터링 의미를 유지하는 일련의 변환 과정을 통해서 코드를 향상하는 개발 방법
- 계약에 의한 설계 루틴이 선행 조건과 후행 조건을 갖고 있다고 생각하는 개발 방법.