合成/聚合复用原则

♦合成/聚合复用原则(Composite/Aggregate Reuse Principle,CARP)经常又叫做合成复用原则(Composite Reuse Principle,CRP)。

♦合成/聚合复用原则就是在一个新的对象里面使用一些已有的对象,使之成为新对象的一部分,新的对象通过向这些对象的委派达到复用已有功能的目的。简言之:要尽量使用合成/聚合,尽量不要使用继承

♦合成和聚合的区别:

  • 聚合用来表示”拥有“关系或者整体与部分的关系;
  • 合成用来表示一种强得多的”拥有“关系,其部分与整体的生命周期是一样的。

♦复用的基本种类:

  • 组合/聚合:可以使系统更加灵活,降低类与类之间的耦合度,一个类的变化对其他类造成的影响相对较少。“黑箱”复用。

  • 继承:需要严格遵循里氏代换原则,滥用继承反而会增加系统构建和维护的难度以及系统的复杂度。继承复用会破坏系统的封装性。“白箱”复用。

♦复用时要尽量使用组合/聚合关系(关联关系),少用继承。

♦如果两个类之间是“Has-A”的关系应使用组合或聚合,如果是“Is-A”关系可使用继承

  • ”Is-A“是严格的分类学意义上的定义,意思是一个类是另一个类的”一种“。
  • ”Has-A“表示某一角色具有某一项责任。

 举例说明:

Sunny软件公司开发人员在初期的CRM系统设计中,考虑到客户数量不多,系统采用MySQL作为数据库,与数据库操作有关的类如CustomerDAO类等都需要连接数据库,连接数据库的方法getConnection()封装在DBUtil类中,由于需要重用DBUtil类的getConnection()方法,设计人员将CustomerDAO作为DBUtil类的子类,初始设计方案结构如图所示:

 根据结构图写出部分C#代码片段如下:

... ...
class DBUtil
{
    public Connection getConnection()
    {
        ... ...
    }
}

class CustomerDAO: DBUtil
{
    public void addCustomer()
    {
        base.getConnection();
    }
}
... ...

随着客户数量的增加,系统决定升级为Oracle数据库,因此需要增加一个新的OracleDBUtil类来连接Oracle数据库,由于在初始设计方案中CustomerDAO和DBUtil之间是继承关系,因此在更换数据库连接方式时需要修改CustomerDAO类的源代码,将CustomerDAO作为OracleDBUtil的子类,这将违反开闭原则。【当然也可以修改DBUtil类的源代码,同样会违反开闭原则。】现使用合成复用原则对其进行重构。

根据合成复用原则,我们在实现复用时应该多用关联,少用继承。因此在本实例中我们可以使用关联复用来取代继承复用,重构后的结构如图所示:

在图中,CustomerDAO和DBUtil之间的关系由继承关系变为关联关系,采用依赖注入的方式将DBUtil对象注入到CustomerDAO中,可以使用构造注入,也可以使用Setter注入。如果需要对DBUtil的功能进行扩展,可以通过其子类来实现,如通过子类OracleDBUtil来连接Oracle数据库。由于CustomerDAO针对DBUtil编程,根据里氏代换原则,DBUtil子类的对象可以覆盖DBUtil对象,只需在CustomerDAO中注入子类对象即可使用子类所扩展的方法。例如在CustomerDAO中注入OracleDBUtil对象,即可实现Oracle数据库连接,原有代码无须进行修改,而且还可以很灵活地增加新的数据库连接方式。

根据结构图写出部分C#代码如下:

... ...
class DBUtil
{
    public Connection getConnection()
    {    
        ... ...
    }
}

class OracleDBUtil: DBUtil
{
    public Connection getConnection()
    {
        ... ...
    }
}

class CustomerDAO
{
    private DBUtil util = new DBUtil();
    public void addCustomer()
    {
        util.getConnection();
    }
}
... ...

【参考:《Java与模式》】

【参考:https://blog.csdn.net/lovelion/article/details/7563441】

猜你喜欢

转载自www.cnblogs.com/wangtao1211/p/12526885.html
今日推荐