티스토리 뷰
필요성
불변 클래스는 가변 클래스보다 설계하고 구현하고 사용하기 쉬우며, 오류가 생길 여지도 적고 훨씬 안전하다
불변 클래스를 만드는 다섯 가지 규칙
1. 객체의 상태를 변경하는 메서드를 제공하지 않는다
2. 클래스를 확장할 수 없도록 한다 (final class)
3. 모든 필드를 final로 선언한다 (JLS 17.5)
4. 모든 필드를 private으로 선언한다
5. 자신 외에는 내부의 가변 컴포넌트에 접근할 수 없도록 한다
- 만약 제공해야 한다면 방어적인 복사 사용
불변 클래스의 장점과 단점
- 함수형 프로그래밍에 적합하다
- 피연산자에 함수를 적용한 결과를 반환하지만 피연산자가 바뀌지는 않는다
- 불변 객체는 단순하다
- 불변 객체는 근본적으로 스레드 안전하여 따로 동기화할 필요 없다
- 불변 객체는 안심하고 공유할 수 있다
- 상수, public static final
- 불변 객체 끼리는 내부 데이터를 공유할 수 있다
- 객체를 만들 때 불변 객체로 구성하면 이점이 많다
- 실패 원자성을 제공한다
- 어떤 오퍼레이션을 수행하다가 예외가 발생해도 원래 데이터가 변경되지 않음
- 단점) 값이 다르다면 반드시 별도의 객체(새로운 인스턴스)로 만들어야 한다
- "다단계 연산"을 제공하거나, "가변 동반 클래스"를 제공하여 대처할 수 있다 (StringBuilder)
불변 클래스를 만들 때 고려할 것
- 상속을 막을 수 있는 또 다른 방법
- private 또는 package-private 생성자 + 정적 패터리
- 확장이 가능하다. 다수의 package-private 구현 클래스를 만들 수 있다
- 정적 팩터리를 통해 여러 구현 클래스 중 하나를 활용할 수 있는 유연성을 제공하고 객체 캐싱 기능으로 성능을 향상 시킬 수도 있다
- 재정의가 가능한 클래스는 방어적인 복사를 사용해야 한다
- 모든 "외부에 공개하는" 필드가 final이어야 한다
- 계산 비용이 큰 값은 해당 값이 필요로 할 때 (나중에) 계산하여 final이 아닌 필드에 캐시해서 쓸 수도 있다

