클래스 체계
- 변수
- public static
- private static
- private
- 함수
- 공개 함수
- 비공개 함수
- 비공개 함수는 자신을 호출하는 공개함수 직후에 넣자.
- 캡슐화
- 캡슐화를 최우선시 하자.
테스트 코드에 꼭 필요하다면 함수나 변수를 protected로 선언하거나, 패키지 전체로 공개할 수도 있다.
- 캡슐화를 최우선시 하자.
클래스 생성시 고려할 사항
1. 클래스는 작아야 한다.
얼마나 작아야 하는가?
위 질문이 떠오른다면, 해법은 간단하다. 클래스가 맡은 책임을 세자.
책에서는 SuperDashboard 클래스를 예시로 들었다.
내가 생각한 예제는 주방 가전 제품이다. 만약 아래의 기능을 모두 가진 가전 제품이 있다면 어떨까
- 밥을 한다
- 빵을 굽는다.
- 달걀 후라이도 가능하다.
- 빙수를 만들 수 있다.
기능이 너무 많다 보니, "어떤 가전제품"이라고 딱 짚어서 이야기하기 힘들다.
만약 클래스 명에 'if', 'or', 'and', 'but'등의 단어, 즉 기능 설명이 복잡해지는 단어가 들어가서 이름이 모호해진다면, 클래스를 나눌 때다.
2. 단일 책임 원칙(Single Responsibility Princile. SRP)을 지키자.
클래스나 모듈을 변경할 이유는 한가지어야한다.
즉, 클래스는 하나의 책임만 명확히 가지고 있어야 한다.
3. 클래스 내 응집도(cohesion)가 높아야 한다.
프로그램의 한 요소가 특정 목적을 위해 서로 밀접하게 연관되어 묶여 있어야 한다.
그런데, 함수를 작게, 매개변수 목록을 작게 만들다보면 클래스 인스턴스 변수를 많이 만들게 된다. 그 결과 몇 함수만 사용하는 변수 여러개가 클래스 내에 나열된다. 그 결과 응집도가 낮아진다. 이 경우, 응집도를 높히기 위해 클래스를 여러개로 분리하자.
4. 클래스 간 결합도(coupling)가 낮아야 한다.
5. 변경으로 부터 격리되어있어야한다.
- 변화가 잦은 로직은 외부에서 주입받자.
- 클래스는 상세한 구현이 아니라 추상화에 의존해야한다. (Dependency Injection Principal. DIP)
* 예) 아래 코드는 구체적인 로직을 포트폴리오에서 분리한 모습이다.
// 예시. 주식 시세에 따라 포트폴리오가 달라진다. 이 때 주식 시세는 나라마다 다르다.
// 주식 시세
public interface StockExchange {
Money currentPrice(String symbol);
}
// 포트폴리오는 주식 시세 정책을 알지 못한다. 다만 외부에서 주입받을 뿐이다. (dependency injection)
public Portfolio {
private StockExchange exchange;
public Portfolio(StockExchange exchange) {
this.exchange = exchange;
}
// ...
}
정리
테스트가 가능할 정도로 시스템의 결합도(coupling)을 낮추어, 클래스의 재사용성과 유연성을 높이자.
'개발 > 클린코드' 카테고리의 다른 글
5. 형식 (0) | 2021.08.21 |
---|---|
4장. 주석 (0) | 2021.08.21 |
[요약] 3. 함수 (0) | 2021.08.14 |
[요약] 2.의미 있는 이름 (0) | 2021.08.14 |
[요약] 1장. 깨끗한 코드 (0) | 2021.08.14 |