设计模式原则:组合/聚合复用原则

2023-08-10 14:42:52 浏览数 (1)

组合/聚合复用原则

组合/聚合复用原则表示在一个新的对象里通过关联关系(组合关系或者聚合关系)来使用一些已有的对象,使之成为新对象的一部分;新对象通过委派调用已有对象的方法达到复用其已有功能的目的。也就是说,要尽量使用组合或者聚合,而不是使用继承来达到复用的目的。

组合/聚合复用原则是面向对象设计的重要原则之一,它体现了类之间的关联和组合。如果一个软件能够遵循组合/聚合复用原则,那么它就具有以下两个优点:

  • 降低了类之间的耦合性,提高了系统的灵活性。
  • 提高了代码的可重用性,避免了继承带来的缺点。

举个例子,假设我们有一个动物类 Animal,它有一个方法 eat(),表示动物可以吃东西。然后我们定义了一个狗类 Dog 和一个鸟类 Bird 来继承 Animal 类,并实现 eat() 方法。但是,我们发现狗类和鸟类还有一些其他的行为,比如狗可以叫,鸟可以飞。这些行为和 eat() 方法没有什么关系,但是却被放在了同一个类中。代码如下:

代码语言:javascript复制
class Animal {
    public void eat() {
        System.out.println("动物可以吃东西");
    }
}

class Dog extends Animal {
    @Override
    public void eat() {
        System.out.println("狗吃骨头");
    }

    public void bark() {
        System.out.println("狗会叫");
    }
}

class Bird extends Animal {
    @Override
    public void eat() {
        System.out.println("鸟吃虫子");
    }

    public void fly() {
        System.out.println("鸟会飞");
    }
}

这个类违反了组合/聚合复用原则,因为它使用了继承来达到复用的目的。这样的设计有以下几个缺点:

  • 类之间的耦合度高,如果 Animal 类发生变化,就会影响到所有继承它的类。
  • 代码的可重用性差,因为 Animal 类包含了一些不必要的方法。
  • 代码的灵活性差,如果我们想要增加新的动物类型或者新的行为,就需要修改 Animal 类或者继承它的类。

为了遵循组合/聚合复用原则,我们应该将 Animal 类设计成一个接口,并定义一个抽象方法 eat()。然后,针对不同的动物类型和行为,定义不同的类来实现 Animal 接口或者组合其他类。这样,在程序中可以根据需要选择实现哪些接口或者组合哪些类,而不强制继承不必要的接口或者类。代码如下:

代码语言:javascript复制
interface Animal {
    public void eat();
}

class Dog implements Animal {
    private Barkable barkable;

    public Dog(Barkable barkable) {
        this.barkable = barkable;
    }

    @Override
    public void eat() {
        System.out.println("狗吃骨头");
    }

    public void bark() {
        barkable.bark();
    }
}

class Bird implements Animal {
    private Flyable flyable;

    public Bird(Flyable flyable) {
        this.flyable = flyable;
    }

    @Override
    public void eat() {
        System.out.println("鸟吃虫子");
    }

    public void fly() {
        flyable.fly();
    }
}

interface Barkable {
    public void bark();
}

interface Flyable {
    public void fly();
}

class BigDog implements Barkable {
    @Override
    public void bark() {
        System.out.println("大狗汪汪叫");
    }
}

class SmallDog implements Barkable {
    @Override
    public void bark() {
        System.out.println("小狗呜呜叫");
    }
}

class Eagle implements Flyable {
    @Override
    public void fly() {
        System.out.println("老鹰在天空飞");
    }
}

class Sparrow implements Flyable {
    @Override
    public void fly() {
        System.out.println("麻雀在树上飞");
    }
}

// 其他动物类型和行为的实现类省略

0 人点赞