如何通过策略模式简化ifelse?
10月26日 暗影泪投稿 哈喽,大家好,我是难瓜。
相信大家日常开发中会经常写各种分支判断语句,比如ifelse,当分支较多时,代码看着会比较臃肿,那么如何优化呢?1。什么是策略模式?
Defineafamilyofalgorithms,encapsulateeachone,andmaketheminterchangeable。Strategyletsthealgorithmvaryindependentlyfromclientsthatuseit。
策略模式(StrategyPattern):定义一族算法类,将每个算法分别封装起来,让它们可以互相替换。2。策略模式定义
Context封装角色
它也叫做上下文角色,起承上启下的封装作用,屏蔽高层模块对策略、算法的直接访问,封装可能存在的变化。
Strategy抽象策略角色
策略、算法家族的抽象,通常为接口,定义每个策略或算法必须具有的方法和属性。
ConcreteStrategy具体策略角色
实现抽象策略中的操作,该类含有具体的算法。3。策略模式通用代码publicclassContext{抽象策略privateS构造函数设置具体策略publicContext(Strategystrategy){this。}封装后的策略方法publicvoiddoAnything(){this。strategy。doSomething();}}publicinterfaceStrategy{策略模式的运算法则publicvoiddoSomething();}publicclassConcreteStrategy1implementsStrategy{OverridepublicvoiddoSomething(){System。out。println(ConcreteStrategy1);}}publicclassConcreteStrategy2implementsStrategy{OverridepublicvoiddoSomething(){System。out。println(ConcreteStrategy2);}}
测试:publicclassStrategyClient{publicstaticvoidmain(String〔〕args){声明一个具体的策略StrategystrategynewConcreteStrategy1();声明上下文对象ContextcontextnewContext(strategy);执行封装后的方法context。doAnything();}}4。用策略模式改写ifelse
假设我们要处理一个office文件,分为三种类型docx、xlsx、pptx,分别表示Word文件、Excel文件、PPT文件,根据文件后缀分别解析。4。1常规写法publicclassOfficeHandler{publicvoidhandleFile(StringfilePath){if(filePathnull){}StringfileExtensiongetFileExtension(filePath);if((docx)。equals(fileExtension)){handlerDocx(filePath);}elseif((xlsx)。equals(fileExtension)){handlerXlsx(filePath);}elseif((pptx)。equals(fileExtension)){handlerPptx(filePath);}}publicvoidhandlerDocx(StringfilePath){System。out。println(处理docx文件);}publicvoidhandlerXlsx(StringfilePath){System。out。println(处理xlsx文件);}publicvoidhandlerPptx(StringfilePath){System。out。println(处理pptx文件);}privatestaticStringgetFileExtension(StringfilePath){解析文件名获取文件扩展名,比如文档。docx,返回docxStringfileExtensionfilePath。substring(filePath。lastIndexOf(。)1);returnfileE}}
处理逻辑全部放在一个类中,会导致整个类特别庞大,假设我们要新增一种类型处理,比如对于2007版之前的office文件,后缀分别是docxlsppt,那我们得增加elseif逻辑,违反了开闭原则,如何解决这种问题呢,答案就是通过策略模式。4。2策略模式改写publicinterfaceOfficeHandlerStrategy{voidhandlerOffice(StringfilePath);}publicclassOfficeHandlerDocxStrategyimplementsOfficeHandlerStrategy{OverridepublicvoidhandlerOffice(StringfilePath){System。out。println(处理docx);}}
省略OfficeHandlerXlsxStrategyOfficeHandlerPptxStrategy类publicclassOfficeHandlerStrategyFactory{privatestaticfinalMapString,OfficeHandlerStrategymapnewHashMap();static{map。put(docx,newOfficeHandlerDocxStrategy());map。put(xlsx,newOfficeHandlerXlsxStrategy());map。put(pptx,newOfficeHandlerPptxStrategy());}publicstaticOfficeHandlerStrategygetStrategy(Stringtype){returnmap。get(type);}}
测试:publicclassOfficeHandlerStrategyClient{publicstaticvoidmain(String〔〕args){StringfilePathC:file123。StringtypegetFileExtension(filePath);OfficeHandlerStrategystrategyOfficeHandlerStrategyFactory。getStrategy(type);strategy。handlerOffice(filePath);}privatestaticStringgetFileExtension(StringfilePath){解析文件名获取文件扩展名,比如文档。docx,返回docxStringfileExtensionfilePath。substring(filePath。lastIndexOf(。)1);returnfileE}}4。策略模式优点
算法可以自由切换
这是战略模式本身定义的,只要实现抽象策略,它就成为策略家族的一个成员,通过封装角色对其进行封装,保证对外提供自由切换的策略。
避免使用多种条件判断
简化多种ifelse,或多个switchcase分支。
扩展性良好
增加一个策略,只需要实现一个接口即可。5。策略模式应用场景
多个类型只有在算法或行为上稍有不同的场景。
算法需要自由切换的场景。
需要屏蔽算法规则的场景。
投诉 评论