ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • SOLID Principles
    학교생활/소프트웨어디자인패턴 2023. 10. 13. 11:39
    728x90

    102 - 8. SRP 단일 책임 원칙

    SRP(Single Responsibility Principle) 에서 책임(Responsibility) 는 바로 변경에 대한 책임이다!

    따라서 클래스를 변경할 때 클래스를 변경하는 이유가 하나만 존재하도록 해야한다.

     

    SRP 는 모듈이나 클래스의 변경을 야기하는 응집력과 같은 개념이다. 만약 한 클래스가 하나 이상의 책임을 맡는다면(low cohesion), 한 책임에 대한 변경은 다른 책임을 충족시키는 클래스의 능력을 떨어뜨리거나 저하 시킬 수 있다. 이런 종류의 결합은 변경을 했을 때 예상치 못한 방식으로 잘못 동작하는 취약한 설계를 유발한다. 

     

    클래스나 모듈 내에서 비슷한 개념들의 관계는 tight 해야한다. SRP 를 준수해서 변경을 하면 응집도가 높아진다. 그러면서 다른 클래스나 모듈과는 lose coupling 이 된다. 이는 퍼블릭한 인터페이스로 만들 수 있다.

     

     

    106 - 9. OCP 개방 폐쇄 원칙

    Fool me once, shame on you,
    Fool me twice, shame on me.

     

    처음에는 코드가 변경되지 않을 것이라 생각하고 코드를 작성한다.

    한 번에 모든 일을 해결할 수 없으니 첫 번째는 괜찮다.

    하지만 변경이 일어나면 나중에 일어날 그런 종류의 변경으로부터 보호하는 추상화를 구현해야 한다.

    그래서 그 다음부터는 문제를 방지한다.

    추상화를 안해서 초래하는 그 이후부터 일에 대한 잘못은 내 탓이다.

     

    OCP 를  준수하는 다른 전략으로는 TDD 와 Fast Iteration 이 있다.

    빠른 반복 주기로, 수시로 클라이언트에게 공개했을 때,끊임없는 피드백을 받을 수 있게 된다. 그리고 더 나은 디자인을 만들어 낼 수 있다.

     

     

    111 - 10. LSP 리스코프 치환원칙

    [정사각형과 직사각형]

    정사각형은 직사각형일 수 있지만, actor 의 관점에서 볼때, 정사각형 객체는 직사각형 객체가 아니다. 왜냐하면 정사각형 객체의 행위가 actor 가 기대하는 직사각형의 행위와 일치하지 않기 때문이다. 행위 측면에서 볼 때, 정사각형은 직사각형이 아니다. 그리고 행위야 말로 소프트웨어의 모든 것이다. 

     

    기반 클래스보다 덜한 동작을 하는 파생 클래스는 보통 그 기반 클래스와 치환이 불가능하므로 LSP 를 위반한다.

    기반 클래스가 발생시키지 않는 예외를 파생 클래스의 메소드에 추가하면 LSP 위반이다. (= 치환 가능하지 않아진다.)

     

    166 - 11. DIP 의존 관계 역전 원칙

    DIP(의존 관계 역전 원칙)는 상위 수준의 모듈이 하위 수준의 모듈에 의존해서는 안되며,  둘 다 추상화에 의존해야 한다는 원칙이다. 
    DIP 가 중요한 이유는, DIP 를 활용하여 의존성 구조가 역전되면 재사용 및 확장에 유리해지기 때문이다.
    반면 DIP 를 위반하며, 즉 상위 수준의 모듈이 하위 수준의 모듈에 의존하면, 하위 모듈의 변경이 상위 모듈에 직접적인 영향을 미칠 수 있고, 심지어 상위 수준의 모듈이 별경될 수도 있다.
    상위 수준의 모듈의 어플리케이션은 본질을 담고 있기 때문에, 상위 수준에서 많은 변경이 일어나면 안된다.

    동적 다형성(즉, 추상 클래스나 인터페이스)를 이용해서 의존성의 역전을 해결할 수 있다.

     

     

    177 - 12. ISP 인터페이스 분리 원칙

    '하나의 일반적인 인터페이스 보다는, 여러 개의 구체적인 인터페이스가 낫다'

    클래스의 상속을 이용하여 인터페이스를 분리한다.

    위임을 이용하여 인터페이스를 나눌 수 있다.

     

    더보기

    Q. OCP 의 기본아이디어는 무엇이고 이것을 어떻게 달성하겠다는 이야기인가? 설명하라.
    모든 시스템은 생명주기에 따라 계속해서 변화한다.
    OCP 는, 소프트웨어 개체가 요구사항이 변경될 때 모듈을 확장할 수 있어야 하며, 이 행위가 소스코드에 변경을 초래하지 않아야 한다는 것을 의미한다.
    OCP 를 달성하는 방법은 추상화이다. 인터페이스나 추상클래스처럼 일반화를 통한 추상화를 한다.
    그렇게 되면 모듈은 추상화에 의존하기때문에 수정에 대해서는 닫혀있고, 추상화의 새 파생 클래스를 만듦으로써 확장이 가능하다.
    또한 LSP 는 OCP를 가능하게하는 요인 중 하나이다. 상속을 통해 모듈의 수정 없이도 서브 타입의 치환을 통해 확장이 가능해진다.
    // TDD 나 fast iteration 도 가능
    // tools: 추상, 캡슐, 상속, 다형성, dip(매캐니즘), lsp(insurance)

    Q. DIP 는 무엇이고 이것이 왜 중요한지 설명 해보아라.
    DIP(의존 관계 역전 원칙)는 상위 수준의 모듈이 하위 수준의 모듈에 의존해서는 안되며,  둘 다 추상화에 의존해야 한다는 원칙이다. 
    DIP 가 중요한 이유는, DIP 를 활용하여 의존성 구조가 역전되면 재사용 및 확장에 유리해지기 때문이다.
    반면 DIP 를 위반하며, 즉 상위 수준의 모듈이 하위 수준의 모듈에 의존하면, 하위 모듈의 변경이 상위 모듈에 직접적인 영향을 미칠 수 있고, 심지어 상위 수준의 모듈이 별경될 수도 있다.
    상위 수준의 모듈의 어플리케이션의 본질을 담고 있기 때문에, 상위 수준에서 많은 변경이 일어나면 안된다.

     

     

    [참고]

    https://velog.io/@__dan_n/클린-소프트웨어-chapter-8.-단일-책임-원칙SRP-chapter-9.-개방-폐쇄-원칙OCP

    https://velog.io/@__dan_n/클린-소프트웨어-chapter-10.-리스코프-치환-원칙-LSP

    https://velog.io/@__dan_n/클린-소프트웨어-chapter-11.-의존-관계-역전-원칙-DIP-chapter-12.-인터페이스-분리-원칙-ISP

    https://velog.io/@ljinsk3/디자인-패턴-Strategy-Pattern

    https://m.blog.naver.com/younari0604/220948568622

    728x90
Designed by Tistory.