您的位置:

依赖注入的三种实现方式详解

一、依赖注入的三种实现方式 php

依赖注入是一种编程技术,目的是为了降低耦合性、提高可测试性和可扩展性,它可以将对象之间的依赖关系从程序中抽象出来并在外部进行管理,从而使程序更加灵活。而在 php 中,实现依赖注入有三种方式,分别是构造器注入、属性注入、方法注入。

构造器注入


class Person{
    public function __construct(Car $car){
        $this->car = $car;
    }
}
$car = new Car();
$person = new Person($car);

构造器注入是一种通过类的构造器方法接收依赖对象的方式。在上述代码中,Person 类需要一个 Car 类的实例,所以在其构造器中声明了一个参数 $car,通过参数传递的方式将 Car 的实例传递给了 Person 的构造器,而 Person 对象在实例化时则会自动将传入的 Car 实例赋值给自己的 $car 属性。

属性注入


class Person{
    public $car;
}
$car = new Car();
$person = new Person();
$person->car = $car;

属性注入是一种通过声明类的公共属性来接收依赖对象的方式。通过公共属性直接将Car类的实例赋值给Person类的属性 $car,实现依赖注入。

方法注入


class Person{
    public $car;
    public function setCar(Car $car){
        $this->car = $car;
    }
}
$car = new Car();
$person = new Person();
$person->setCar($car);

方法注入是一种通过类的公共方法来接收依赖对象的方式。Person 类中声明了一个 setCar 方法,通过方法传递 Car 的实例并将其赋值给 $car 属性,实现依赖注入。

二、依赖注入的两种实现方式

构造器依赖注入


class Person{
    public function __construct(Car $car){
        $this->car = $car;
    }
}
$car = new Car();
$person = new Person($car);

构造器依赖注入,在构造函数中依赖对象

Setter 方法依赖注入


class Person{
    public $car;
    public function setCar(Car $car){
        $this->car = $car;
    }
}
$car = new Car();
$person = new Person();
$person->setCar($car);

Setter 方法依赖注入,在 Setter 方法中依赖对象

三、依赖注入的三种实现方式区别

构造器依赖注入:类似于参数传入,它将依赖关系放到构造函数中,使代码更加清晰明了,并且遵循了单一职责原则。容易维护和测试,但是在依赖链过长时,代码可读性会下降。如果创建新对象时初始化参数缺失,则需要重载构造函数并传入缺失的参数。

Setter 方法依赖注入:Setter 方法依赖注入是在代码运行期间通过 Setter 方法设置依赖关系。相比于构造器注入,Setter 方法依赖注入更加灵活,可以省略一些必需的参数,而且对于可选依赖项也能更好地支持。缺点是它隐藏了类的依赖关系,难以确定依赖的位置,代码可读性差。

属性注入:属性注入是一种非常简单的依赖注入方法,但是它的缺点在于实现上的灵活性差,在某些情况下会破坏封装性,降低代码的可测试性。而且属性注入容易让人忽略依赖关系,导致类之间产生紧密的耦合。

四、依赖注入的三种实现方式的优缺点

构造器注入的优缺点

优点:

1. 遵循了单一职责原则;

2. 依赖关系直观。

缺点:

1. 构造函数的参数数量容易增多;

2. 构造函数多次调用会导致性能问题。

Setter 方法注入的优缺点

优点:

1. 灵活性比较高,可以在对象实例化后动态修改对象;

2. 在依赖环节比较棘手的情况下,可以通过 Setter 方法注入来像拼图一样解决。

缺点:

1. Setter 方法可能会被滥用,使得类的依赖关系更加难以理解;

2. 需要修改对象状态,会影响对象的一致性和不可变性;

3. 依赖关系不可见。

属性注入的优缺点

优点:

1. 比较简单容易理解;

2. 在创建对象实例时仅需要一行代码。

缺点:

1. 会破坏对象的封装性;

2. 对象的创建和依赖关系之间易混淆;

3. 依赖关系不可见。

五、依赖注入的三种方式

构造器注入


class Person {
        private $car;
        public function __construct(Car $car) {
            $this->car = $car;
        }
    }
    $car = new Car();
    $person = new Person($car);

Setter 方法注入


class Person{
        private $car;
        public function setCar(Car $car){
            $this->car = $car;
        }
    }
    $car = new Car();
    $person = new Person();
    $person->setCar($car);

属性注入


class Person{
        public $car;
    }
    $car = new Car();
    $person = new Person();
    $person->car = $car;

六、spring 常用的三种注入方式

Setter 注入

将依赖项暴露为符合 JDK Java Bean 规范的 Bean 属性导出,并通过 Bean 属性设置进行注入。

构造器注入

在 Bean 定义文件中声明构造器函数,并将 Bean 的依赖项传递给构造器函数。

Auto-wiring 注入

自动装配是一种通过 Spring 容器自动确定 Bean 依赖关系的方法。在自动装配过程中,Spring 容器会自动将 Bean 之间的依赖关系映射到相应的 Bean 属性或构造器参数上。

七、总结

依赖注入是一种为了降低耦合性、提高可测试性和可扩展性的编程技术。在 php 中,有三种实现依赖注入的方式,分别是构造器注入、属性注入、方法注入。这三种方式各有优缺点,需要根据具体业务场景选择合适的实现方式。

在 spring 中,常用的三种实现依赖注入的方式是 Setter 注入、构造器注入、Auto-wiring 注入,相对于 php 中的实现方式,更加灵活和复杂,但也更加强大。