[아이템1]생성자보다 정적 팩터리 메서드를 써야하는 이유
이펙티브 자바 책을 읽으면서 새로 알게된 내용이나 느낀점을 정리한 글입니다.
일반적으로 객체를 생성할 때는 생성자를 이용한 new 키워드를 통해 객체를 생성한다.
필자가 처음 자바를 배울 때도 그렇게 하라고 배웠다.
그런데 이 책에서는 생성자보다 정적 팩터리 메서드를 통해 만드는 것을 권장하고 있다.
PS. 정적 팩터리 메서드란?
-> 간단히 말하면 메서드를 통해 객체를 생성하는 것을 정적 팩터리 메서드라고 한다.
아래는 LocalTime 의 정적 팩터리 메서드의 예시이다.
public static LocalTime of(int hour, int minute) {
ChronoField.HOUR_OF_DAY.checkValidValue((long)hour);
if (minute == 0) {
return HOURS[hour];
} else {
ChronoField.MINUTE_OF_HOUR.checkValidValue((long)minute);
return new LocalTime(hour, minute, 0, 0);
}
}
생성자를 private 으로 숨기고 정적 팩터리 메서드를 썼을 때 장점은 다음과 같다.
1. 이름을 가질 수 있다.
생성자는 이름이 객체 이름으로 강제되는 반면, 정적 팩터리 메서드는 매개변수를 받아서 해당 매개변수 특성에 맞는 객체를 만드는 등의 역할을 할 수 있다. 이름으로 어떤 특성을 가진 객체가 반환되는 지 알면 협업을 할 때 다른 사람이 만든 코드를 사용하기가 한 층 수월해질 것이다.
참고로 필자는 네이밍의 가치를 처음에 "그렇게 중요한건가...? 대충 알아들으면 되겠지...ㅎ" 하면서 중요하게 생각안하곤 했는데 회사에서 코드리뷰를 받으면서 네이밍은 협업을 할 때 매우 중요한 요소중에 하나라고 리뷰를 받은 적이 있었다.
2. 호출될 때마다 인스턴스를 새로 생성하지는 않아도 된다.
팩터리 메서드 안에서 객체를 꼭 new 로 새로 만들어서 던져줄 필요는 없다.
미리 만들어둔 객체를 던져준다거나 하여 객체 생성비용을 아낄 수 있다.
3. 하위타입의 객체를 반환할 수 있는 능력이 있다.
객체를 리턴할 때 메서드기 때문에 반환할 객체를 자유롭게 선택가능하다는 유연성을 제공한다.
4. 입력 매개변수에 따라 매번 다른 클래스의 객체를 반환할 수 있다.
위와 비슷한 얘기일 수 있는데 상황에 맞게 다른 클래스, 또는 자식 객체를 반환시킬 수 있는데
이것의 장점은 클라이언트는 어떤 하위 클래스가 반환되었는지 몰라도 된다는 것이다.
예를 들면 입력받은 매개변수를 더 최적화하여 처리할 수 있는 자식객체를 새로 만들어 클라이언트에게 던져줘도 클라이언트는 부모만 알기 때문에 코드에 문제없이 성능 개선을 할 수 있다.
하지만 정적 팩터리 메서드로 할 때 장점만 있는 것은 아니다.
아래와 같이 단점또한 존재한다.
1. 정적 팩터리 메서드만 제공하면 하위 클래스를 만들 수 없다.
상속을 하려면 public 이나 protected 와 같은 생성자가 필요한데 이럴 때 자식 클래스를 못만들게 된다.
하지만 의도적으로 상속을 막고 불변타입으로 객체를 만들고자 할 때 오히려 장점이 될수도 있는 부분이다.
2. 정적 팩터리 메서드는 프로그래머가 찾기 힘들다.
일반적으로 프로그래머들은 객체를 생성하고자 할 때 생성자를 찾게 되는데 정적 팩터리 메서드는 발견하기 힘들다는 단점이 있다.
따라서 API 문서나 팀원들간에 공유가 잘 되어야 할 것이다.
생성자대신 정적 팩터리 메서드를 통해 객체를 생성할때는 상황에 맞게 장단점을 판단해서 작성하면 될 것 같다.
참고로 아래는 정적 팩터리 메서드를 만들때 쓰는 네이밍 방식들이다.
- from : 하나의 매개 변수를 받아서 객체를 생성
- of : 여러개의 매개 변수를 받아서 객체를 생성
- getInstance | instance : 인스턴스를 생성. 이전에 반환했던 것과 같을 수 있음.
- newInstance | create : 새로운 인스턴스를 생성
- get[OtherType] : 다른 타입의 인스턴스를 생성. 이전에 반환했던 것과 같을 수 있음.
- new[OtherType] : 다른 타입의 새로운 인스턴스를 생성.
'독서 > Effective Java' 카테고리의 다른 글
[아이템3]싱글턴을 만들거면 확실히 만들자! (0) | 2021.11.02 |
---|---|
[아이템2]생성자에 매개변수가 많을 때는? 빌더 패턴을 쓰자! (0) | 2021.11.02 |