[도서] 실전 자바 소프트웨어 개발 - Chapter2 입출금 내역 분석(SRP 활용)
"책을 보면서 정리한 내용입니다." 틀린 내용이 있다면 댓글 부탁드립니다.
chapter2에서는 객체지향 개발 원칙 중 SRP(단일 책임 원칙)에 대한 챕터이다.
테스트코드도 나오지만 SRP가 주된 내용이기에 SRP에 집중하여 글을 작성하였다.
SRP(Single Responsibility Principle) - 단일 책임 원칙??
SRP는 하나의 클래스는 하나의 책임만을 가진다는 원칙
- 일반적으로 SRP는 클래스와 메서드에 적용한다.
- 소프트웨어의 유지보수성을 높이고 오류의 범위를 최소화 할 수 있다.
- 코드가 변경되는 이유를 한 가지로 제한할 수 있다.
해당 책에서 SRP를 위반 하는 안티 패턴으로는 아래의 두 가지를 설명하고 있다.
갓 클래스
- 한 개의 파일에 모든 코드를 구현한 것이고, 한 클래스로 모든 것을 해결하려는 패턴이다.
- 즉, 해당 클래스의 기능이 모호해지고 이해하기 어려워지는 것이다.
ex) 입출금 내역 분석기
30-01-2017,-100, Deliveroo와 같은 입출금 내역 분석을 하기 위한 여러 기능들이 한 클래스에 모여있는 것
=> 문자열 파싱, 입출금액 합
코드 중복
- 하나의 문제만 해결하도록 하드코딩 되어있다.
- 문제 해결 전략이 변경된다면 이를 해결하기위해 코드의 거의 모든 곳에서 변경이 일어나거나 약간의 기능만 변경된 코드를 중복되게 작성할 수도 있다.
ex) CSV 파일을 분석해야하는데 문제해결전략이 JSON 형식의 데이터를 파싱해야한다면??
코드로 살펴보자
=> 한줄한줄이 30-01-2017,-100, Deliveroo 형식인 CSV 파일을 분석하는 코드
위의 코드를 보면 아래와 같은 작업들이 모여있다.
- 파일에서 라인 읽어오기
- 각 라인별 콤마로 열 분리
- amount 가져오고 double로 파싱
- amount 총합 구하기
- 출력하기
당연히 코드는 수행이 되고 총합을 구한다는 목적은 달성할 수 있다.
하지만 구하고자 하는 것이 달라진다면 전체적인 코드의 수정은 불가피해질 것이다.
가령, 특정 월별 amount 총합을 가져오고 싶다면 반복문 내부에서 날짜의 월을 파싱하고 이를 if문을 통해 해결해야할 것이다.
코드의 문제점
- "columns"라는 모호한 파싱 결과
- 기능별로 분리되어 있지 않은 코드들
1번 문제 해결
파싱한 데이터를 나타내는 도메인 클래스를 작성하여 해결하면 코드의 가독성 및 유지보수성을 향상시킬 수 있다.
2번 문제 해결
각 기능별로 클래스를 활용하여 그룹화를 진행하면 SRP 원칙을 준수할 수 있다.
전달된 각 line을 도메인 객체로 생성하고 이를 List로 만들어 반환하는 클래스이다.
이렇게 한다면 내가아닌 다른 사람이 볼 때도 파싱하는 각 요소가 어떤 것인지 확실하게 알 수 있고 해당 클래스는 데이터 파싱이라는 하나의 책임만을 지기에 SRP를 준수한다고 할 수 있다.
또한 amount를 합하는 로직도 분리해야 한다.
위와 같이 분리할 수 있고 필요한 기능이 추가된다면 해당 클래스에 메서드를 추가함으로써 if문을 통한 분기를 막을 수 있다.
기능별로 클래스를 분리한다면 main문은 line을 분리하는 작업 이외에는 다른 작업이 어떻게 구현되었는지는 알 수 없다. 또한 알 필요도 없고 해당 기능을 그냥 사용하면 되는 것이다. 그리고 오류가 난다고 해도 오류의 범위가 하나의 클래스에 한정되므로 유지보수성도 올라간다.
Chapter2 정리
- 갓 클래스와 코드 중복은 코드를 추론하고 유지보수하기 어렵게 만드는 요인이다.
- SRP는 관리하고 유지보수하기 쉬운 코드를 구현하는 데 도움을 준다.
- 높은 응집도와 낮은 결합도는 유지보수가 가능한 코드가 가져야 할 특징이다.
"막간 지식 정리"
결합도
서로 다른 모듈 간에 상호 의존하는 정도 또는 연관된 관계를 의미한다. 즉, 다른 클래스와의 상호 연관성을 의미하는데
해당 클래스를 변경하는데 의존하는 다른 클래스도 변경이 많이 일어난다면 결합도가 높다고 할 수 있다. 결합도는 낮을 수록 좋다.
응집도
응집도는 한 모듈 내부의 처리 요소들이 서로 관련되어 있는 정도를 말한다. 즉, 모듈이 독립적인 기능을 수행하는지 또는 하나의 기능을 중심으로 책임이 잘 뭉쳐있는지를 나타내며 모듈이 높은 응집도를 가질 수록 좋다.