본문 바로가기

reviews/Clean Code

13. 동시성

동시성은 결합을 없애는 전략이다. 즉, 무엇과 언제를 분리하는 전략이다.

동시성

  • 동시성은 때로 성능을 높여준다.
  • 동시성을 구현하면 설계가 판이하게 달라진다.
  • 컨테이너가 어떻게 동작하는지, 어떻게 동시 수정, 데드락 등과 같은 문제를 피할 수 있는지 알아야 한다.
  • 다소 부하를 유발한다.
  • 복잡하다.
  • 동시성 버그는 재현하기 어렵다.

동시성 방어 원칙

단일 책임 원칙 Single Responsibility Principle, SRP
: 주어진 메서드/클래스/컴포넌트를 변경할 이유가 하나여야 한다는 원칙
  • 동시성을 구현할 때 고려해야 하는 것

    • 동시성 코드는 독자적인 개발, 변경, 조율 주기가 있다.
    • 동시성 코드에는 독자적인 난관이 있다.
    • 잘못 구현한 동시성 코드는 별의별 방식으로 실패한다.
  • 자료 범위를 제한하라.
    객체 하나를 공유한 후 동일 필드를 수정하던 두 스레드가 서로 간섭하므로 예상치 못한 결과를 내놓는다.
    해결방안으로 공유 객체를 사용하는 코드 내 임계영역을 syncronized 키워드로 보호하라고 권장한다.

    • 임계영역의 수가 많을 때 발생할 수 있는 경우
      • 보호할 임계영역을 빼먹기 쉽다.
      • 모든 임계영역을 올바로 보호했는지 확인하느라 똑같은 노력과 수고를 반복하기 쉽다.
      • 버그를 찾기가 더 어려워진다.
        권장사항 => 자료를 캡슐화하여 공유자료를 최대한 줄여라.
  • 자료 사본을 사용하라

  • 스레드는 가능한 독립적으로 구현하라.
    다른 스레드와 자료를 공유하지 않는다. 각 스레드는 클라이언트 요청 하나를 처리한다. 모든 정보는 비공유 출처에서 가져오며 로컬 변수에 저장한다.

라이브러리를 이해하라

  • 스레드 환경에 안전한 컬렉션을 사용하라.
  • 서로 무관한 작업을 수행할 때는 executor 프레임워크를 사용하라.
  • 가능하다면 스레드가 차단되지 않는 방법을 사용하라.
  • 일부 클래스 라이브러리는 스레드에 안전하지 못하다.

스레드 환경에 안전한 컬렉션을 사용하라.

예시 > java.util.concurrent 패키지가 제공하는 클래스 ConcurrentHashMap

  • 거의 모든 상황에서 HashMap보다 빠르고, 동시 읽기/쓰기를 지원하며, 자주 사용하는 복합 연산을 다중 스레드 상에서 안전하게 만든 메서드로 제공한다.

동기화하는 메서드 사이에 존재하는 의존성을 이해하라.

동기화하는 메서드 사이에 의존성이 존재하면 동시성 코드에 찾아내기 어려운 버그가 생긴다.
공유 객체 하나에는 하나의 메서드만 사용하며, 불가피 한 상황에는 아래 세가지 방법을 고려하라.
-    클라이언트에서 잠금
-    서버에서 잠금
-    연결 서버 (잠금을 수행하는 중간 단계 서버)

동기화 하는 부분을 작게 만들어라

자바에서 synchronized 키워드를 사용하여 락을 설정할 수 있다. 이를 남발하면 스레드를 지연시키고 부하를 가중시키므로 바람직하지 않다. 반면, 임계영역은 반드시 보호해야하므로 코드를 짤 때는 임계영역 수를 최대한 줄여야 한다.

올바른 종료 코드는 구현하기 어렵다.

깔끔하게 종료하는 코드는 올바로 구현하기 어렵다.
스레드가 절대 오지 않을 시그널을 기다리는 '데드락'을 주의하라.

스레드 코드 테스트하기

문제를 노출하는 테스트 케이스를 작성하라. 프로그램 설정과 시스템 설정과 부하를 바꿔가며 자주 돌려라. 발생했던 버그가 다시 돌렸더니 통과하더라도 이유를 찾지 않고 그냥 넘어가면 안된다.
프로세서 수보다 많은 스레드를 돌려보아라.
코드에 보조 코드를 넣어 강제로 실패를 일으켜봐라.

발생했던 버그가 다시 돌렸더니 통과하더라도 이유를 찾지 않고 그냥 넘어가면 안된다!...ㅎ

반응형

'reviews > Clean Code' 카테고리의 다른 글

15. JUnit 들여다보기  (0) 2021.02.23
14. 점진적인 개선  (0) 2021.02.08
12. 창발성  (0) 2021.02.02
11. 시스템  (0) 2021.01.26
10. 클래스  (0) 2021.01.26