🌟

依存性逆転の原則(Dependency Inversion Principle)とは

に公開

✅ 依存性逆転の原則とは?

依存性逆転の原則(Dependency Inversion Principle) は、オブジェクト指向設計における SOLID原則 の一つです。基本的な考え方は次の通りです:

高水準のモジュールは低水準のモジュールに依存してはならない。両者は抽象に依存すべきである。抽象は詳細に依存してはならない。詳細が抽象に依存すべきである。

簡単に言うと、「具体的な実装に依存せず、インターフェース(抽象)を通じてやり取りすべき」という考え方です。これにより、柔軟でテストしやすく、保守しやすいコードになります。

🌟 具体例

❌ 依存性逆転の原則を使っていない場合(悪い例)

// 低水準モジュール:キーボード
class Keyboard {
    public String getInput() {
        return "ユーザー入力(キーボード)";
    }
}

// 高水準モジュール:コンピュータ
class Computer {
    private Keyboard keyboard = new Keyboard(); // 具体クラスに依存

    public void input() {
        System.out.println(keyboard.getInput());
    }
}

このコードでは、Computer クラスは Keyboard に直接依存しており、将来 TouchScreen や VoiceInput に切り替えたい場合は Computer クラスを修正する必要があります。拡張性が低い設計です。

✅ 依存性逆転の原則を適用した場合(良い例)

// 抽象:入力デバイスインターフェース
interface InputDevice {
    String getInput();
}

// 低水準モジュール1:キーボード
class Keyboard implements InputDevice {
    public String getInput() {
        return "ユーザー入力(キーボード)";
    }
}

// 低水準モジュール2:タッチスクリーン
class TouchScreen implements InputDevice {
    public String getInput() {
        return "ユーザー入力(タッチスクリーン)";
    }
}

// 高水準モジュール:コンピュータ
class Computer {
    private InputDevice inputDevice;

    // コンストラクタで依存を注入
    public Computer(InputDevice inputDevice) {
        this.inputDevice = inputDevice;
    }

    public void input() {
        System.out.println(inputDevice.getInput());
    }
}

使用例:

public class Main {
    public static void main(String[] args) {
        InputDevice device = new Keyboard(); // または new TouchScreen()
        Computer computer = new Computer(device);
        computer.input();
    }
}

🎯 この設計のメリット

  • Computer(高水準モジュール)は Keyboard や TouchScreen(低水準モジュール)に直接依存しません。

  • 新しいデバイス(例:VoiceInput)を追加する場合でも、InputDevice を実装するだけでOKです。

  • 単体テストが簡単になります(モックで InputDevice を差し替え可能)。

補足

下記の記事のように、DDDではドメインレイヤはインフラレイヤに依存せず、domain -> infraIF <- infraImpl のように I/F によって DIP で実現する
https://qiita.com/k_yamaki/items/bf99d3bf64a84258a3a1#依存関係逆転の法則

Discussion