[Java] 정적 팩토리 메서드란?

popolarburr·2023년 4월 9일
0

우리는 보통 생성자를 이용해 객체의 인스턴스를 만들곤 한다.

class A {
	public A() {
    	...
    }
}
...

...

A a = new A(); 

이렇게 만드는 것이 보통적인 일이다. 그러나 정적 팩토리 메서드를 이용해서도 객체 인스턴스를 만들 수 있다. 즉, 객체 인스턴스를 만드는 하나의 클래스 메서드라고 볼 수 있다.


class A {
	
    public static A of() {
    	return new A();
    }
}

...

...

A a = a.of();

이렇게 사용하면 좋은점은 무엇일까?

우선 이름을 가질 수 있다. 우리는 객체 인스턴스를 생성할때, 생성자를 사용하게되면 클래스의 이름에 해당하는 생성자를 통해 생성한다.

A a = new A();

그러나 정적 팩토리 메서드를 사용하게 되면 of같은 이름을 가질 수 있다는 장점이 있다.

또한 클래스 객체 내에 같은 데이터 타입의 필드가 여러개 있고, 선택적으로 사용한다고 가정할 때, 골라서 사용할 수 있다.

예를들어,

public class Order {

	private boolean prime;
    private boolean urgent;
    private Product product;
    
}

라는 클래스가 존재한다 가정하다.
주문이라는 클래스는 prime, urgent, product를 필드로 갖는다. 여기서 prime과 urgent를 같은 데이터 타입(boolean)으로 가지고있다. 이때, 이 중 하나만 필요로하여 하나만 사용한다고 가정하면

public class Order {

	private boolean prime;
    private boolean urgent;
    private Product product;
    
    public Order(Product product, boolean prime) { .. }
    
}

이런 식으로 사용할 수 있다. 또한 다른 boolean인 urgent만 필요로하여 생성자를 또 만들어준다면 이런식으로 할 수 있다.

public class Order {

	private boolean prime;
    private boolean urgent;
    private Product product;
    
    public Order(Product product, boolean prime) { .. }
	public Order(Product product, boolean urgent) { .. }
    
}

하지만 이렇게 작성하면 컴파일에러가 나타난다. 왜? 생성자의 파라미터 명을 생략하고, 같은 데이터 타입이 두개 작성되었기 떄문이다. Product와 boolean. 물론 파라미터명은 다르지만
자바는 이를 같다고 판단하여 컴파일 에러를 발생시킨다.

이는 이미 정의되었다고 판단한다.

물론 생성자의 파라미터 순서를 바꾸는 방식으로 이러한 에러를 우회할 순 있다. 근본적인 해결은 아니고.

또한 이러한 생성자는 클래스의 이름을 토대로 만들어지기때문에 필요한 필드만을 골라서 작성할 때 의미가 모호해질 수 있다.

그럴때 사용하는 것이 정적 팩토리 메서드 이다.

우선 사용 예시를 보자.

public class Order {

	private boolean prime;
    private boolean urgent;
    private Product product;
    
	public static Order primeOrder(Product product, boolean urgent) {
    	Order order = new Order();
        order.prime = true;
        order.product = product;
        return order;
    }
    
    public static Order urgentOrder(Product product, boolean urgent) {
    	Order order = new Order();
        order.urgent = true;
        order.product = product;
        return order;
    }
    
}

아주 가볍게 예시를 작성해봤다.

이렇게 하면 아주 직관적이지 않나?

static으로 작성된 정적 팩토리 메서드는 외부에서 primeOrder,urgentOrder를 통해 직관적으로 알기쉬우며, 상황과 목적에 맞게 원하는 필드값만을 활용해서 객체 인스턴스를 생성하여 넘길 수 있다.

각각의 코드를 보게되면 primeOrder는 prime과 product만을, urgentOrder는 urgent와 product만을 새로운 Order 인스턴스에 필드를 초기화하여 return한다.

이렇게 사용하면 외부에서 객체를 생성할 때도 원하는 것, 혹은 필요한 것만을 넣어 생성할 수 있겠다는 직관성이 생긴다.

profile
차곡차곡

0개의 댓글