1:什么是开放封闭原则
开放封闭原则(Open-Closed Principle):一个软件实体应当对扩展开放(open),则修改关闭(不修改原来的代码这就是closed)。在设计一个模块时,应当使得这个模块可以在不被修改的前提下被扩展(这就要求我们不能在一个类中写死所有的功能)。也就是说,应当可以在不必修改源代码的情况下修改这个模块的行为。设计的目的便在于面对需求的改变而保持系统的相对稳定,从而使得系统可以很容易的从一个版本升级到另一个版本,也许我们做一个项目不难,难就难在后期不断变态的需求上把你搞死,如果设计不好的话会大量修改原来的代码,这样会造成一个类中的代码巨大,而且还容易导致新的bug,
也许我们不能做到完全封闭,那我们就应该对那些变化封闭,那些变化隔离做出选择。我们做出选择,然后将那些无法封闭的变化抽象出来,进行隔离允许扩展,尽可能的减少系统的开发.当系统变化来临时,我们要及时的做出反应。我们并不害怕改变的到来。当变化到来时,我们首先需要做的不是修改代码,而是尽可能的将变化抽象出来进行隔离,然后进行扩展。面对需求的变化,对程序的修改应该是尽可能通过添加代码来实现,而不是通过修改代码来实现
这样文字讲解也许太抽象现在通过一个实例来演示下这个问题:
一个银行业务员有这些功能,
package com.zhimore.bank;
/**
* 银行业务员
* @author Adminis
*/
public class BankWorker {
/**
* 存款
*/
public void saving(){
System.out.println("进行存款操作");
}
/**
* 取款
*/
public void drawing(){
System.out.println("进行 取款操作");
}
public void transfer(){
System.out.println("进行转账操作");
}
/**
* 基金申购
*/
public void fundSubscription(){
System.out.println("进行基金申购操作");
}
}
package com.zhimore.bank;
public class MainClass {
public static void main(String[] args) {
BankWorker bankWorker = new BankWorker();
bankWorker.saving();
bankWorker.drawing();
bankWorker.fundSubscription();
bankWorker.transfer();
}
}
打印的结果:
进行存款操作
进行 取款操作
进行基金申购操作
进行转账操作
也许你会说这样功能不是实现了么,感觉么么哒,但是如果后期经理说小周给这个银行业务员添加一个办理信用卡的功能,那你是不是又要到BankWorker类中去写个办理信用卡的方法用来实现这个功能呢?也许后期会有n个功能要添加,那你一直在原来的类中去写,你能保证不会出错,而且扩展性和维护性都很差,所以一个功能过来最好是别再之前的类中去添加新的功能了,这样就要求你开始设计的时候就要考虑后期的扩展,而且最好要做到不在原来的代码上做修改,这就是我们本博客要讲的原则 开放-封闭原则,就是对扩展开放,对修改关闭,怎么做到扩展和关闭呢?其实也不难,你只要把功能抽取出来,对后期的功能添加一个新的类去实现这样就不需要修改之前的代码,而且不容易出错,代码也清晰,
新的设计如下:
上面银行业务员仅仅是一个接口,下面各种办理都是一个个子类去实现
package com.zhimore.bank1;
/**
* @author Adminis
*/
public interface BankWorker {
public void operation();
}
我们把银行的各个业务抽取出来一个接口,
package com.zhimore.bank1;
/**
* 负责取款操作的业务员
* @author Adminis
*/
public class DrawingBankWorker implements BankWorker {
@Override
public void operation() {
System.out.println("进行 取款操作");
}
}
package com.zhimore.bank1;
/**
* 存款业务员
* @author Adminis
*/
public class SavingBankWorker implements BankWorker {
@Override
public void operation() {
System.out.println("进行存款操作");
}
}
package com.zhimore.bank1;
/**
* 负责转账操作的业务员
* @author Adminis
*/
public class TransferBankWorker implements BankWorker{
@Override
public void operation() {
System.out.println("进行转账操作");
}
}
package com.zhimore.bank1;
public class MainClass {
public static void main(String[] args) {
BankWorker bank1 = new SavingBankWorker();
bank1.operation();
BankWorker bank2 = new DrawingBankWorker();
bank2.operation();
BankWorker bank3 = new TransferBankWorker();
bank3.operation();
}
}
打印结果:
进行存款操作
进行 取款操作
进行转账操作
这样设计也实现了上述功能,但是扩展性更好,比如要添加某一个功能我们只需要添加一个类实现BankWorker接口就行,这样是不是做到了对外扩展,对内进行关闭,因为我们并没有修改原来的代码,而只是在原来的基础上添加了几个类,这就是扩展,
2:开放封闭原则的优越性
1.通过扩展已有的软件系统,可以提供新的行为,以满足对软件的新需求,是变化中的软件有一定的适应性和灵活性。
2.已有的软件模块,特别是最重要的抽象模块不能再修改,这就使变化中的软件系统有一定的稳定性和延续性