공부하는 블로그
2024 08 16 TIL IoC와 DI 본문
스프링 관련 글들을 볼 때 많이 봤던 IoC와 DI를 공부하게 되었다.
1. 좋은 코드란?
- 논리가 간단해야함.
- 중복되는 코드를 제거하고 표현이 명확해야 한다.
- 누구나 쉽게 수정할 수 있게 가독성이 좋아야 한다.
- 의존성을 최소화 한다.(느슨한 결합)
- 기능을 추가하더라도 크게 구조의 변경이 없어야 한다.
IoC와 DI를 활용하면 이러한 좋은 코드를 짤 수 있다고 한다.
2. 디자인 패턴과 설계 원칙
디자인 패턴 : 소프트웨어에서 자주 발생하는 문제들을 해결하기 위한 재사용 가능한 솔루션
설계 원칙 : 소프트웨어 시스템을 설계할 때 따라야 할 일반적인 규칙이나 가이드라인
여기서 IoC는 디자인 패턴이고 DI는 설계 원칙이고, DI 패턴을 사용해서 IoC 설계원칙을 구현하고 있다.
3. DI(Dependency Injection) : 의존성 주입
객체 지향 프로그래밍에서 객체가 자신이 의존하는 객체를 직접 생산하지 않고, 외부에서 주입받는 설계 패턴.
의존성 주입에는 크게 3가지의 주입 방식이 있다.
- 필드에 직접 주입
더보기
public class Consumer {
Food food;
void eat() {
this.food.eat();
}
public static void main(String[] args) {
Consumer consumer = new Consumer();
//Chicken 객체를 생성하고, Consumer의 food 필드에 주입
consumer.food = new Chicken();
consumer.eat(); //"치킨을 먹는다." 출력
consumer.food = new Pizza();
consumer.eat(); //"피자를 먹는다." 출력
}
}
interface Food {
void eat();
}
class Chicken implements Food{
@Override
public void eat() {
System.out.println("치킨을 먹는다.");
}
}
class Pizza implements Food{
@Override
public void eat() {
System.out.println("피자를 먹는다.");
}
}
- Setter를 통한 주입
더보기
public class Consumer {
Food food;
void eat() {
this.food.eat();
}
//Setter
public void setFood(Food food) {
this.food = food;
}
public static void main(String[] args) {
Consumer consumer = new Consumer();
//Setter를 이용한 의존성 주입
consumer.setFood(new Chicken());
consumer.eat();
consumer.setFood(new Pizza());
consumer.eat();
}
}
interface Food {
void eat();
}
class Chicken implements Food{
@Override
public void eat() {
System.out.println("치킨을 먹는다.");
}
}
class Pizza implements Food{
@Override
public void eat() {
System.out.println("피자를 먹는다.");
}
}
- 생성자를 통한 주입
더보기
public class Consumer {
Food food;
//생성자
public Consumer(Food food) {
this.food = food;
}
void eat() {
this.food.eat();
}
public static void main(String[] args) {
//생성자를 이용한 의존성 주입
Consumer consumer = new Consumer(new Chicken());
consumer.eat();
consumer = new Consumer(new Pizza());
consumer.eat();
}
}
interface Food {
void eat();
}
class Chicken implements Food{
@Override
public void eat() {
System.out.println("치킨을 먹는다.");
}
}
class Pizza implements Food{
@Override
public void eat() {
System.out.println("피자를 먹는다.");
}
}
4. IoC(Inversion of Control) : 제어의 역전
프로그램의 제어 흐름을 개발자가 아닌 프레임워크나 외부 환경에 맡기는 것.
예시코드)
public class Consumer {
void eat() {
Chicken chicken = new Chicken();
chicken.eat();
}
public static void main(String[] args) {
Consumer consumer = new Consumer();
consumer.eat();
}
}
class Chicken {
public void eat() {
System.out.println("치킨을 먹는다.");
}
}
이런 코드를 사용했다면 Consumer가 직접 음식 객체를 만들어야 했기 때문에 다른 메뉴를 먹고싶으면 eat 메서드를 수정했어야 했다.
(제어의 흐름 Consumer -> food)
하지만 의존성 주입을 통해 만들어진 음식을 Consumer 객체에게 전달해주는 식으로 변경함으로써 Consumer는 따로 코드 수정 없이
어떤 음식이 되었든 그냥 의존성 주입해서 먹을 수 있게 되었다. (제어의 흐름 : food -> Consumer)
'내일배움캠프 > TIL' 카테고리의 다른 글
2024 08 22 TIL 한 번 더 엔티티 관련 정리 (0) | 2024.08.23 |
---|---|
2024 08 19 TIL : 영속성 컨텍스트 (0) | 2024.08.20 |
2024 08 12 TIL DTO로 서버와 데이터 주고받기 (0) | 2024.08.13 |
2024 08 09 TIL : Spring MVC에 대해 (0) | 2024.08.12 |
2024 08 08 TIL : Javadoc과 주석달기 (0) | 2024.08.09 |