聚合和依赖注入之间的差异

时间:2017-01-20 14:21:39

标签: php oop design-patterns dependency-injection aggregation

我最近研究了依赖注入设计模式。

class User
{

private $db;

public function __construct(Database $db) 
{
        $this->$db = $db;
}

}

我不禁想知道这是我在聚合中学到的相同的事情。如果我错了,请纠正我。我知道依赖注入 目标 聚合 不同。有什么我想念的吗?

5 个答案:

答案 0 :(得分:2)

  

我不禁想知道这与我在聚合中学到的东西相同

考虑一个Department类,例如,有Professor个对象数组作为实例变量。有两种方法可以使用一些Professor对象初始化教授数组。

  1. 您可以通过说ProfessorDepartment,在某些不带参数的方法中初始化professors[0]=new Professor("CK");类中professors[1]=new Professor("MK");数组的元素。
  2. 您可以提供一个构造函数,该构造函数将Professor类型的数组作为其参数。任何想要实例化Department的类都必须将Professor个对象数组传递给构造函数。
  3. 聚合:使用选项1或2来定义Department如何获得其教授并不重要。即使没有部门(假设教授属于多个部门),教授也将继续存在,因此无论教育部门如何获得教授,这都被认为是聚合。

    依赖注入如果使用选项2创建Department实例,则将其称为依赖注入。一个部门需要教授,你通过在Department课程之外提供它来实现这种依赖。

    换句话说,聚合是一种关系类型,可以使用选项1或选项2(或其他选项,例如从数据库中获取教授并填充{{1})来建模在方法内的Professor中的数组)。依赖注入是设计类的方法,以便可以从类外部提供其依赖项。可以对聚合关系建模以支持依赖注入,但这并不意味着聚合依赖注入是相同的。

答案 1 :(得分:1)

聚合通常被建模为一对多关系,而且往往意味着部分整体语义。由于这些原因,用户数据库通常被视为聚合:关系是1:1,用户的概念不一定意味着数据库。

将此与汽车及其车轮的常见聚合示例进行对比。有一对多的关系,汽车的概念通常意味着它有轮子。

依赖注入可以被认为是创建关系的方式。关系可以是1:1或一对多。它可能意味着某些语义,或不是。 DI的关键特征是User不能控制DB的创建,也不会启动它的创建。

实际上,聚合关系通常可以通过依赖注入来创建;但这并不意味着这两个概念是等价的。 DI可以创建其他类型的关系,并且可以在没有DI的情况下创建聚合。

答案 2 :(得分:1)

聚合是一种维护对象之间关联的方法。在描述对象之间构造关系的方式时,可以使用此术语。它是一个域名术语,现实生活中物体之间存在着同样的关系。

依赖注入是一种在对象之间管理依赖关系的方法,以实现松散耦合。可以在聚合中使用相同的技术。但通常,在聚合中,它不是关于耦合,而是关于对象如何相关。这个术语也有现实生活中的类比,但它们主要用来解释什么是控制反转,通常,你的域名没有对应关系。

答案 3 :(得分:1)

聚合是一种对象组合形式。它与依赖注入无关。

另一方面,依赖注入并不是关于对象如何关联,而是如何将其他对象(依赖关系)转换为特定对象。 依赖关系可以是聚合,服务,存储库,验证器,文字......

通常,在强类型语言中, dependencies 作为接口引入,以避免将对象与实现细节耦合。相反,在动态类型语言中,约定和强大的文档可以构建一个良好且紧密耦合的依赖图。

请注意,数据库不能是聚合。并非所有关联都被视为聚合,而您可以考虑注入依赖

无论如何,你的推理中有一些设计气味:用户不应该依赖数据库,但如果数据层/数据映射层是注入你的用户实体的更好的候选者,您将实施active record pattern之类的内容。

答案 4 :(得分:1)

我决定添加这些要点。

如果我从你的角度思考你应该问这个问题,因为聚合& 依赖注入提升可以放入其他实体的实体,也可以单独工作。

但是有区别。在 聚合 中,您正在使用直接对象。即维持状态,生命周期等的物体。

例: 灯泡&间

  • 灯泡的实例可以放入房间的实例中。
  • 但不仅房间,某些情况可以放入汽车广播等实例。
  • Bulb 的实例也可以独立工作,而不会被放入其他对象的实例中。

但是在 依赖注入 中,我们专注于类级别的交互。这与纯OOP实践有些不同。实际上在DI中我们倾向于将 无状态类 (工作者类)注入到其他类中。虽然它们看起来像对象,但它们实际上只是被注入的无状态类。该类的实例也可以独立存在。 DI被广泛用作 Traditional Singleton Pattern 的替代品,因为传统方式有一些负面的副作用。

前:

假设一个名为 StringUtils 的无状态工作者类(不是使用静态方法堆叠的apache)。它可以注入名为 NounUtils VerbUtils 等的类中。 StringUtils 的实例也可以存在。

希望你有个主意。 :))