제리 devlog

[이펙티브자바] 인터페이스는 타입을 정의하는 용도로만 사용하라 본문

Java

[이펙티브자바] 인터페이스는 타입을 정의하는 용도로만 사용하라

제리 . 2021. 1. 11. 19:19

인터페이스 : 클래스가 어떤 인터페이스를 구현한다는 것은 자신의 인스턴스로 무엇을 할 수 있는지를 클라이언트에게 전달하는 것이다. 인터페이스는 오직 이 용도로만 사용해야한다.

 

인터페이스를 잘못 사용한 예 )상수 인터 페이스

 

상수 인터페이스란 메서드 없이 static final 필드로만 가득한 인터페이스를 말한다. 클래스에 정규화된 이름을 쓰는걸 피하고자 종종 사용한다고함

public interface PhysicalConstants {
  //아보가도르 수(1/몰)
  static final double AVOGADROS_NUMBER = 6.002_140_857e23;  //_기호는 숫자 리터럴의 값에는 영향을 주지않고 읽기는 훨씬 간편하게 해줌

  //볼츠만 상수 (J/K)
  static final double BOLTZMANN_CONSTANT = 1.380_648_52e-23;

  // 전자 질량 (kg)
  static final double ELECTRON_MASS = 9.109_383_56e-31;
}

 

 

클라이언트는 상수 인터페이스의 값에 직접 접근할 수 있음

인터페이스에서 protected도 불가!!
protected static final double AVOGADROS_NUMBER = 6.002_140_857e23;

-> 불필요한 정보를 노출하는 행위 오히려 클라이언트가 혼란할 수 있음

 

클라이언트는 상수 인터페이스의 값으로 새로운 로직을 만들 수 있음

-> 다음 릴리스때 인터페이스의 값이 바뀐다면 클라이언트 어플리케이션에 문제발생

public class Calculator implements PhysicalConstants{
  public double cal1(int input){
    return input * AVOGADROS_NUMBER;
  }

  public double cal2(int input){
    return input * BOLTZMANN_CONSTANT;
  }

  public double cal3(int input){
    return input * ELECTRON_MASS;
  }
}

 public static void main(String[] args) {
    Calculator calculator = new Calculator();
    double myResult = 100 * calculator.AVOGADROS_NUMBER; //문제 발생
  }

대안

상수 유틸리티 클래스를 제공

public class PhysicalConstants {
  
  //인스턴스화 방지
  private PhysicalConstants(){};
  
  //아보가도르 수(1/몰)
  protected static final double AVOGADROS_NUMBER = 6.002_140_857e23;

  //볼츠만 상수 (J/K)
  static final double BOLTZMANN_CONSTANT = 1.380_648_52e-23;

  // 전자 질량 (kg)
  public static final double ELECTRON_MASS = 9.109_383_56e-31;
}

public class Calculator{
  public double cal1(int input){
    return input * PhysicalConstants.AVOGADROS_NUMBER;
  }

  public double cal2(int input){
    return input * PhysicalConstants.BOLTZMANN_CONSTANT;
  }

  public double cal3(int input){
    return input * PhysicalConstants.ELECTRON_MASS;
  }
}

 

enum 활용

public enum PhysicalConstants {
  AVOGADROS_NUMBER(6.002_140_857e23), //아보가도르 수(1/몰)
  BOLTZMANN_CONSTANT(1.380_648_52e-23), //볼츠만 상수 (J/K)
  ELECTRON_MASS(9.109_383_56e-31); // 전자 질량 (kg)

  private double value;

  PhysicalConstants(double value) {
    this.value = value;
  }

  public double getValue(){
    return value;
  }
}


public class Calculator{
  public double cal1(int input){
    return input * PhysicalConstants.AVOGADROS_NUMBER.getValue();
  }

  public double cal2(int input){
    return input * PhysicalConstants.BOLTZMANN_CONSTANT.getValue();
  }

  public double cal3(int input){
    return input * PhysicalConstants.ELECTRON_MASS.getValue();
  }
}

 

결론

인터페이스는 타입을 정의하는 용도로만 사용해야 한다. 상수 공개용 수단으로 사용하지는 말자.

Comments