You will be fine

<이펙티브 자바> 4. 클래스와 인터페이스

by BFine
반응형

www.yes24.com/Product/Goods/65551284

 

이펙티브 자바 Effective Java 3/E

자바 플랫폼 모범 사례 완벽 가이드 - Java 7, 8, 9 대응자바 6 출시 직후 출간된 『이펙티브 자바 2판』 이후로 자바는 커다란 변화를 겪었다. 그래서 졸트상에 빛나는 이 책도 자바 언어와 라이브

www.yes24.com

15 접근권한 최소화하자

  • 내부 구현정보를 외부 컴포넌트로 부터 얼마나 잘숨겼나가 중요

  • 정보은닉의 장점

    • 여러 컴포넌트를 병렬 개발하여 개발속도를 높인다.
    • 시스템 관리비용을 낮춘다 (각 컴포넌트를을 더 빨리 파악)
    • 소프트웨어 재사용성 높임
    • 전체가 완성 되지 않은 상태에서도 개별 컴포넌트 동작 검증 가능
  • 패키지 외부에서 쓸이유가 없다면 package-private(default)로 쓰자

  • Serializable 구현 클래스는 의도치 않게 공개 API가 될 수 있다.

  • public클래스의 인스턴스 필드는 되도록 public이 아니어야한다.

    • public 가변필드를 갖는 클래스는 일반적으로 스레드 안전하지 않음
  • public static final 배열을 두거나 접근자 메서드를 제공해서는 안된다.

    public static final Thing[] VALUES = {..}; // 보안상 허점 존재
    
    // 방법 1
    private static final Thing[] PRIVATE_VALUES = {..};
    public static final List<Thing> VALUES = Collections.unmodifiableList(Arrays.asList(PRIVATE_VALUES));
    
    // 방법 2 (방어적 복사)
    private static final Thing[] PRIVATE_VALUES = {..};
    public static final Thing[] values(){
      return PRIVATE_VALUES.clone();
    }

16 public class에서는 public 필드가 아닌 접근자 메서드를 사용하자

17 변경가능성을 최소화하자

  • 클래스 불변 규칙
    • 상태를 변경하는 메서드를 제공하지않는다
    • 클래스 확장할 수 없도록 한다.
    • 모든 필드 final, private
    • 자신 외에 내부 가변 컴포넌트에 접근 못하게 한다.
  • final class는 상속을 방지한다
  • getter가 있가고 해서 무조건 setter를 만들지 말자
  • 클래스는 꼭 필요한 경우가 아니라면 불변이어야한다.
  • 다른 합당한 이유가 없다면 모든 필드는 private final 이어야한다.
  • 생성자는 초기화가 완벽히 끝난상태의 객체를 생성해야한다.

18 상속보단 컴포지션을 사용하자

  • 여기서 상속은 클래스가 다른클래스를 확장하는 상속을 의미

    • 상속은 캡슐화를 꺠뜨린다.
    • 상위클래스에 따라 하위 클래스의 동작에 이상이 생길 수 있다.
  • 잘못된 상속

    • HashSet의 addAll 메소드는 add를 사용하므로 두개다 재정의 할경우 문제가 발생한다.
  • 컴포지션 구성

    • 기존 클래스가 새로운 클래스의 구성요소로 쓰이는 구성

    • 포워딩 : 새클래스의 인스턴스 메서드들이 기존 클래스의 대응하는 메서드를 호출해 그결과를 반환

      public class ForwardingSet<E> implements Set<E>{
        private final Set<E> s; 
      }
  • SELF 문제

    • 내부객체는 자신을 감싸고 있는 래퍼의 존재를 모르니 자신을 넘기고 콜백때는 내부 객체를 호출하게 되는 문제

19 상속을 고려해 설계하고 문서화 할꺼아니면 상속금지 시켜라

  • 상속용 클래스는 내부적으로 어떻게 이용하는지 문서로 남겨야한다.

  • @implSpec 태그를 붙여주면 Implementation Requirements 절을 생성한다

  • 상속용으로 설계한 클래스는 하위클래스를 만들어 검증해야한다.

  • 상속용 클래스에서 생성자는 재정의 가능 메서드를 호출해서는 안된다.

    • 상위클래스의 생성자가 먼저실행

      public class SKT {
          public SKT() {
              supOverride();
          }
          public void supOverride(){
              System.out.println("SKT 메서드");
          }
      }
      
      public class SKP extends SKT {
      
          private int a;
          public SKP(){   a = 10; }
      
          @Override
          public void supOverride() {
              System.out.println(a);
          }
      }
      
      public static void main(String[] args) throws ParseException {
          SKP skp = new SKP(); // 0
          skp.supOverride(); // 10
      }
  • Cloneable과 Seralizable 인터페이스는 상속용으로 적합하지 않다.

20 추상클래스 보다는 인터페이스를 우선하자

  • 인터페이스로 계층구조가 없는 타입 프레임워크를 만들 수 있다.
    • implements 로 다중 상속이 가능하기 때문

21 인터페이스는 구현하는 쪽을 생각해 설계하자

  • 디폴드메서드에도 위험이 존재한다.
    • 동기화 문제가 발생할 수 있다?
    • 컴파일에 성공해도 기존 구현체에서 런타임 오류를 일으킬 수 있다.

22 인터페이스 타입을 정의하는 용도로만 사용하자

  • 인터페이스는 자신의 인스턴스로 무엇을 할 수 있는지 클라이언트에게 알려주고 이용로만 써라는 말이다.
  • 상수를 정의하려면 구현체에서 해라 , 불필요한 외부 노출이 발생한다.

23 태그달린 클래스보다는 계층구조를 활용하자

  • 중복 열거 타입, case문을 통한 객체의 타입 구성 등은 태그 클래스는 단점이 많다
    • 가독성 저하, 해당 객체에 불필요한 메서드
    • 장황, 비효율적
  • 태그 클래스는 필요가 없으니 리팩토링하자

24 멤버클래스는 static으로 만들어라

  • 중첩클래스
    • static 멤버, 멤버, 익명, 지역
  • 멤버클래스에 바깥 인스턴스에 접근할 일이 없다면 무조건 static을 붙여라

25 톱레벨 클래스는 한파일에 하나만 담자

반응형

블로그의 정보

57개월 BackEnd

BFine

활동하기