开闭原则(Open-Closed Principle)是指一个软件实体(类,模块和函数)应该对扩展开放,对修改关闭。它是针对扩展和修改两个行为的原则。它强调用抽象构建框架,用实现扩展细节,用以提高系统的可复用性和可维护性,该原则是让在增加新功能的同时尽量不修改已有代码。
几乎任何一款优秀的框架都使用了开闭原则,比如Spring,我们使用Spring的时候不需要修改Spring源代码,就可以集成很多其他框架,增加功能。这里我们使用项目中的微信公众号的消息接收为案例,我们在开发微信公众号时,可以接收微信服务器发来的多种消息:text,image,voice,event等类型的消息,如果一股脑的代码就是一个类处理所有的消息:
public void msgHandler(Wechatmsg wechatMsg) {
String msgType = wechatMsg.getMsgType();
switch(msgType) {
case "text":
break;
case :"voice"
break;
default:
}
}
上面我们处理了微信的两种消息,如果有新需求需要处理图片消息,视频消息等,只能在源代码中接着加case语句,这肯定是违背了开闭原则。开闭原则强调用抽象构建框架,用实现扩展细节,因此我们可以创建微信消息处理接口:
public interface WeChatMsgHandler {
//定义消息类型处理器名称
String getName();
//处理微信消息
void msgHandler(WechatMsg weChatMsg);
}
如果我们想要处理文本消息,则只需要实现该接口即可,如果想要处理其他类型的消息,也只需要实现WeChatMsgHandler接口,完美的实现了开闭原则。
public class WeChatTextMsgHandler implements WeChatMsgHandler {
@Override
public String getName() {
return "text";
}
@Override
public void msgHandler(WechatMsg weChatMsg) {
//处理文本消息
}
}
而前面的复杂的switch case语句则就可以改成如下形式,这样子无论是添加新的消息处理器,还是修改其中的一个消息处理器都不会影响到其他的消息处理。
public void msgHandler(Wechatmsg wechatMsg) {
String msgType = wechatMsg.getMsgType();
//map存储的为WeChatMsgHandler实例,key为WeChatMsgHandler的getName();
WeChatMsgHandler wechatMsgHandler = map.get(msgType);
wechatMsgHandler.msgHandler(weChatMsg);
}
}
开闭原则只是一种原则,可以有很多种实现满足这种原则,代码的实现需要结合具体的场景。