상속보다는 composition

Gunju Kim·2025년 3월 19일
0

필수시청 영상

목록 보기
11/32

🚩 먼저, 핵심 개념부터!

🔹 상속(Inheritance)이란?

  • 클래스 간에 부모-자식 관계를 설정하여, 자식 클래스가 부모 클래스의 속성과 메서드를 물려받는 방식입니다.
  • 코드의 재사용성을 높이지만, 때로는 복잡한 관계와 강한 의존성을 만들어 유지보수가 어려워질 수 있습니다.

🔹 구성(Composition)이란?

  • 클래스가 다른 클래스의 인스턴스를 멤버 변수로 포함하여 재사용하는 방식입니다.
  • 더 유연하고 느슨한 관계를 유지하여 유지보수성이 좋고 확장에 용이합니다.

🚩 왜 상속보다 구성을 많이 사용하게 될까요?

📌 이유 1. 상속은 강력한 결합(Strong coupling)을 유발

  • 자식 클래스가 부모 클래스의 내부 구조에 강하게 의존하게 됩니다.
  • 부모 클래스가 변경되면 자식 클래스가 예기치 않게 영향을 받을 수 있습니다.
  • 코드가 많아질수록 유지보수가 어려워질 수 있습니다.

📌 이유 2. 구성은 느슨한 결합(Loose coupling)을 제공

  • 구성은 다른 객체를 필드로 포함하여 기능을 위임합니다.
  • 클래스 간 독립성을 높여 확장과 변경이 쉬워집니다.
  • 객체의 내부 구현을 숨기고 인터페이스로 소통하므로 변경이 쉽고 안전합니다.

📌 이유 3. 유연성(Flexibility)

  • 구성은 런타임에도 동적으로 객체를 교체하거나 추가할 수 있어 유연성을 높입니다.
  • 상속보다 설계를 변경하기가 쉽고, 새로운 기능을 추가할 때 안정성이 뛰어납니다.

🚩 자바 개발 예시로 보는 비교

자동차(Car) 클래스 예시를 들어볼게요.

✅ 상속을 사용한 경우

// 부모 클래스
class Engine {
    void start() {
        System.out.println("엔진 시동!");
    }
}

// 상속을 이용한 Car 클래스
class Car extends Engine {
    void drive() {
        start();  // Engine 클래스 메서드 사용
        System.out.println("운전 시작!");
    }
}

문제점

  • 자동차가 엔진을 "상속받는다"는 것이 논리적으로 어색합니다.
  • 엔진은 자동차의 일부분이지, 자동차가 엔진을 확장(extend)하는 관계는 아닙니다.
  • 만약 자동차가 전기엔진으로 바뀌거나 다른 엔진이 추가될 경우, 부모 클래스 변경이 어려워집니다.

✅ 구성(composition)을 사용한 경우

// 인터페이스를 통해 느슨한 결합 관계 정의
interface Engine {
    void start();
}

// 엔진 구현체
class GasEngine implements Engine {
    public void start() {
        System.out.println("가솔린 엔진 시동!");
    }
}

class ElectricEngine implements Engine {
    public void start() {
        System.out.println("전기 엔진 시동!");
    }
}

// 구성(Composition)을 이용한 Car 클래스
class Car {
    private Engine engine;

    // 생성자 주입을 통한 Composition
    Car(Engine engine) {
        this.engine = engine;
    }

    void drive() {
        engine.start();
        System.out.println("운전 시작!");
    }
}

장점

  • 자동차는 엔진의 구현체에 의존하지 않고 Engine 인터페이스만 의존합니다.
  • 새로운 엔진을 추가할 때, Engine 인터페이스만 구현하면 됩니다.
  • 코드가 유연하고 확장성이 높으며 변경에 용이합니다.
// 유연한 변경 예시
Car gasCar = new Car(new GasEngine());
gasCar.drive();
// 출력:
// 가솔린 엔진 시동!
// 운전 시작!

Car electricCar = new Car(new ElectricEngine());
electricCar.drive();
// 출력:
// 전기 엔진 시동!
// 운전 시작!
  • 런타임에 엔진 교체가 쉽습니다.
  • 자동차(Car)는 엔진의 세부 구현에 신경 쓸 필요가 없습니다.

🚩 한 줄 요약

자바 개발자뿐만 아니라 대부분의 개발자들은 상속보다 구성을 많이 사용하게 되는데,
이유는 느슨한 결합으로 인해 유연하고, 유지보수하기 쉽고, 확장성과 변경에 용이한 설계가 가능하기 때문입니다.

profile
처음이라서 그래 가본적 없던 길에

0개의 댓글