設計模式之開閉原則示例


  以一個關於課程的例子展示開閉原則:

/**
 * 定義課程接口
 */
public interface ICourse {
    String getName();  // 獲取課程名稱
    Double getPrice(); // 獲取課程價格
    Integer getType(); // 獲取課程類型
}

/**
 * 英語課程接口實現
 */
public class EnglishCourse implements ICourse {

    private String name;
    private Double price;
    private Integer type;

    public EnglishCourse(String name, Double price, Integer type) {
        this.name = name;
        this.price = price;
        this.type = type;
    }

    @Override
    public String getName() {
        return null;
    }

    @Override
    public Double getPrice() {
        return null;
    }

    @Override
    public Integer getType() {
        return null;
    }
}

// 測試
public class Main {
    public static void main(String[] args) {
        ICourse course = new EnglishCourse("小學英語", 199D, "Mr.Zhang");
        System.out.println(
                "課程名字:"+course.getName() + " " +
                "課程價格:"+course.getPrice() + " " +
                "課程作者:"+course.getAuthor()
        );
    }
}

  項目上線,課程正常銷售,但是我們產品需要做些活動來促進銷售,比如:打折。那么問題來了:打折這一動作就是一個變化,而我們要做的就是擁抱變化,現在開始考慮如何解決這個問題,可以考慮下面三種方案:

  1、修改接口

  在之前的課程接口中添加一個方法 getSalePrice() 專門用來獲取打折后的價格;

  如果這樣修改就會產生兩個問題,所以此方案否定

  • ICourse 接口不應該被經常修改,否則接口作為契約的作用就失去了
  • 並不是所有的課程都需要打折,加入還有語文課,數學課等都實現了這一接口,但是只有英語課打折,與實際業務不符
public interface ICourse {

    // 獲取課程名稱
    String getName();

    // 獲取課程價格
    Double getPrice();

    // 獲取課程類型
    String getAuthor();

    // 新增:打折接口
    Double getSalePrice();
}

  2、修改實現類

  在接口實現里直接修改 getPrice()方法,此方法會導致獲取原價出問題;或添加獲取打折的接口 getSalePrice(),這樣就會導致獲取價格的方法存在兩個,所以這個方案也否定。

  3、通過擴展實現變化

  直接添加一個子類 SaleEnglishCourse ,重寫 getPrice()方法,這個方案對源代碼沒有影響,符合開閉原則,所以是可執行的方案,代碼如下,代碼如下:

public class SaleEnglishCourse extends EnglishCourse {

    public SaleEnglishCourse(String name, Double price, String author) {
        super(name, price, author);
    }

    @Override
    public Double getPrice() {
        return super.getPrice() * 0.85;
    }
}

  綜上所述,如果采用第三種,即開閉原則,以后再來個語文課程,數學課程等等的價格變動都可以采用此方案,維護性極高而且也很靈活。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM