객체지향

오브젝트(조영호) 책 정리 -9-

정한_s 2021. 11. 21. 16:25

유연하고 재사용 가능한 설계를 위해 적용할 수 있는 다양한 의존성 원칙

 

개방 폐쇄 원칙

소프트웨어 객체는 확장에 열려있어야 하고 개방에 닫혀 있어야 한다

 

'확장'과 '수정'은 애플리케이션의 '동작'과 '코드'의 관점을 반영한다

 

확장에 대해 열려 있어야 한다 : 애플리케이션의 요구사항이 변경될 때 이 변경에 맞게 새로운 '동작'을 추가해서 애플리케이션의 기능을 확장할 수 있다

 

수정에 대해 닫혀 있다 : 기존의 '코드'를 수정하지 않고도 애플리케이션의 동작을 추가하고 변형할 수 있다.

 

개방-폐쇄 원칙은 런타임 의존성과 컴파일 타임 의존성과 관한 이야기이다. 우리는 컴파일 타임 의존성을 고정시키고 런타임 의존성을 변경해야 한다. 이런 변경을 할 수 있게 하는 것은 '추상화'이다. 공통적인 부분은 수정할 필요가 없어야 하며, 그 외의 부분은 확장 가능하게 해야 한다. 

 

생성과 사용 분리

소프트웨어 시스템은 시작 단계와 실행 단계를 분리해야 한다

 

알아야 하는 지식이 많으면 결합도는 높아진다. 특히 객체 생성에 대한 지식은 과도한 결합도를 초래하는 경향이 있다. 동일한 클래스 안에서 객체 생성과 사용이라는 두 가지 책임을 서로 다른 객체로 분리해야 한다

 

FACTORY 추가하기

객체 생성과 관련된 책임만 전담하는 별도의 객체이다 . 생성과 사용을 분리하기 위해 만들어진 객체이다. 이러한 객체를 통해서 생성의 책임을 FACTORY 객체에게 위임할 수 있다

 

순수한 가공물에게 책임 할당하기 

어떤 책임을 할당하고 싶을 때 제일 먼저 도메인 모델 안의 개념 중에서 적절한 후보가 존재하는지 찾는다. 하지만 적절한 후보가 없다면 전체적으로 결합도를 낮추고 재사용성을 높이기 위해 도메인 개념과 상관없는 가공의 객체를 이용하는 것이 좋다.

이러한 도메인과 무관한 인공적인 객체를 PURE FABRICATION이라고 부른다. 어떤 행동을 추가하는 데 이 행동을 책임질 막당한 도메인 개념이 없다면 인공적인 객체에게 책임을 할당하는 것 좋다.

 

의존성 주입

사용하는 객체가 아닌 외부의 독립적인 객체가 인스턴스를 생성한 후 이를 전달해서 의존성을 해결하는 방법이다.

 

의존성 주입의 종류

생성자 주입 : 객체 생성하는 시점에 생성자를 통한 의존성 해결

setter 주입 : 객체 생성 후 setter 메서드를 통한 의존성 해결

메서드 주입 : 메서드 실행 시 인자를 이용한 의존성 해결

 

숨겨진 의존성은 나쁘다

숨겨진 의존성이 나쁜 이유는 의존성에 관련된 문제가 컴파일타임이 아닌 런타임에 가서야 발견되기 때문이다. 숨겨진 의존성은 코드로 이해하기 어렵고 디버깅하기 어렵다. 

 

의존성 역전 원칙

  • 상위 수준의 모듈은 하위 수준의 모듈에 의존해서는 안 된다. 둘 모두 추상화에 의존해야 한다
  • 추상화는 구체적인 사항에 의존해서는 안 된다. 구체적인 사항은 추상화에 의존해야 한다.

상위 수준의 변경에 의해 하위 수준이 변경되는 것은 납득할 수 있지만 하위 수준의 변경으로 인해 상위 수준이 변경돼서는 곤란하다. 이는 사용과 생성을 모두 추상화에 의존하도록 수정하면 해결할 수 있다. 

* 역전이라고 불린 이유 :  의존성 방향이 전통적인 절차형 프로그래밍 언어와 반대이기 때문에 (추상화-> 구체화) 

 

*유연성에 관하여

유연한 설계는 유연성이 필요할 때만 사용해라

유연성은 항상 복잡성을 수반하다. 반해 유연하지 않은 설계는 단순하고 명확하다. 설계가 유연할수록 클래스 구조와 객체 구조 사이의 거리는 멀어진다. 불필요한 유연성은 불필요한 복잡성을 낳는다.