[OOP] 의존성 주입

Junseo Kim·2021년 3월 28일
0

[OOP]

목록 보기
1/1

의존성 주입이란?

A 클래스가 기능을 수행하기 위해 B클래스의 객체를 필요로 할 때. A클래스는 B클래스의 의존성을 가진다.

public class A {
    private B b; // B클래스의 의존성을 가짐
    
    public A() {
    	this.b = new B();
    }
}

만약 A클래스 내부에서 B클래스 인스턴스를 생성해서 사용한다면 코드의 재활용성이 떨어지며, 결합도가 높아진다.(B클래스가 수정되면 A클래스도 수정해줘야한다)

의존성 주입은 위와 같이 내부에서 인스턴스를 생성하는 것이 아니라, 외부에서 인스턴스를 주입해주는 것이다.

public class A {
    private B b; 
    
    // 생성자를 통한 의존성 주입
    public A(B b) { 
    	this.b = b;
    }
}

이렇게 의존성을 외부에서 주입받으면 아래와 같은 이점을 가진다.

  • 코드의 재활용성이 높아짐
  • 단위테스트가 용이해짐
  • 객체 간의 의존성을 줄여줌
  • 객체 간의 결합도를 낮춰줌

생성자 주입

생성자를 통해 의존 객체를 전달 받는 방식. 객체를 생성하는 시점에 필요한 모든 의존 객체를 준비할 수 있어서 객체 생성 시점에 의존 객체가 정상인지 확인할 수 있다.(검증 작업) 의존 객체가 먼저 생성되어있어야 사용 가능한 방법이다.

public class A {
    private B b; 
    
    // 생성자를 통한 의존성 주입
    public A(B b) { 
    	this.b = b;
    }
}

세터 주입

setter 메서드를 통해 의존성을 주입해주는 방법. 객체를 생성한 뒤에 의존 객체를 주입하게 된다. 의존할 객체가 나중에 생성된다면 이 방법을 사용해야한다. 의존 객체를 설정하지 못한 상태에서 객체를 사용하게 되면 NullPointerException이 발생하게된다.

public class A {
    private B b; 
    
    ...
    
    // setter 메서드를 통한 의존성 주입
    public void setB(B b) {
    	this.b = b;
    }
}

상태를 가지는 객체는 setter를 지양해야하지만(setter를 통해서 변경을 가해도 상관없는 경우만 사용), setter 의존성 주입이 무조건 안 좋은 것은 아니라고 한다.

상태 데이터를 가지는 객체와 상태 데이터를 만드는 행위(메서드)를 가지는 객체를 분리해서 생각해야 한다. 상태 데이터를 만드는 행위를 가지는 객체는 setter를 사용해도 된다.

아래 Cars 클래스는 상태를 가지는 객체이다

public class Cars {
    private RandomNumber randomNumber;
    private final List<Car> cars;
    ...
}

아래 RandomNumber 클래스는 Random을 상태로 가지지만 실제로는 Random 자체보다는 상태 데이터를 만드는 행위(numbers)를 가지는 객체로 보는 것이 맞다.

public class RandomNumber {
    private final Random random;
    ...
    
    public List<Number> numbers(int carSize) {
    ...
    }
}

메서드 주입

필드를 가지고 있지 않고, 해당 메서드가 호출 될 때 의존성을 주입해주는 방법.

public class A {
    
    ...
    
    // 메서드를 통해 의존성 주입 
    public void move(B b) {
    	b.move();
    }
}

메서드를 통해 주입 받다가 한 클래스 내부의 2개 이상의 메서드에서 주입이 필요하다면 필드로 올려줄 수 있다.

참고
[DI] Dependency Injection이란 무엇일까?

0개의 댓글