创建型模式之Strategy模式

简介:

应用场景

实现某一个功能有多种算法或者策略,我们可以根据环境或者条件的不同选择不同的算法或者策略来完成该功能。
如编写排序算法,可以将这些算法写到一个类中,在该类中提供多个方法,每一个方法对应一个具体的查找算法;当然也可以将这些查找算法封装在一个统一的方法中,通过if…else…或者case等条件判断语句来进行选择。这两种实现方法我们都可以称之为硬编码,如果需要增加一种新的查找算法,需要修改封装算法类的源代码;更换查找算法,也需要修改客户端调用代码。在这个算法类中封装了大量查找算法,该类代码将较复杂,维护较为困难。如果我们将这些策略包含在客户端,这种做法更不可取,将导致客户端程序庞大而且难以维护,如果存在大量可供选择的算法时问题将变得更加严重。

策略模式体现了两个非常基本的面向对象设计的原则:
1.封装变化的概念。
2.编程中使用接口,而不是对接口的实现

在JDK中的体现

定义一组算法,并把其封装到一个对象中。然后在运行时,可以灵活的使用其中的一个算法。

java.util.Comparator#compare()
javax.servlet.http.HttpServlet
javax.servlet.Filter#doFilter()

参与角色

环境类(Context):用一个ConcreteStrategy对象来配置。
维护一个对Strategy对象的引用。可定义一个接口来让Strategy访问它的数据。

抽象策略类(Strategy):定义所有支持的算法的公共接口。 
Context使用这个接口来调用某ConcreteStrategy定义的算法。

具体策略类(ConcreteStrategy):以Strategy接口实现某具体算法。

编写策略模式的一般步骤:
1.对策略对象定义一个公共接口
2.编写具体策略类,该类实现了上面的接口
3.在使用策略对象的类(即:环境角色)中保存一个对策略对象的引用
4.在使用策略对象的类中,实现对策略对象的set和get方法(注入)或者使用构造方法完成赋值
5.客户端进行调用

使用策略模式实例

抽象策略类(Strategy):

 

1
2
3
4
5
public  interface  SortStrategy {
     
     public  int [] sort( int [] arr);
 
}

 

具体策略类(ConcreteStrategy):

 

1
2
3
4
5
6
7
8
public  class  InsertionSort  implements  SortStrategy{
 
     @Override
     public  int [] sort( int [] arr) {
         return  arr;
     }
 
}

  

1
2
3
4
5
6
7
8
public  class  SelectionSort  implements  SortStrategy{
 
     @Override
     public  int [] sort( int [] arr) {
         return  arr;
     }
 
}

 

环境类(Context):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
public  class  Context {
     
     private  SortStrategy strategy;
     
      public  Context(SortStrategy strategy){
             this .strategy = strategy;
         }
      
      
      public  void  muiltySort( int [] arr){
             strategy.sort(arr);
         }
 
}

  

策略模式的缺点

1.客户端必须知道所有的策略类,并自行决定使用哪一个策略类;
2.造成很多的策略类;

 


本文转自邴越博客园博客,原文链接:http://www.cnblogs.com/binyue/p/3526498.html,如需转载请自行联系原作者

相关文章
|
安全 Java Spring
【Spring Boot 源码学习】HttpEncodingAutoConfiguration 详解
本篇带大家一起从源码了解 Spring Boot 内置的Http编码功能
245 8
【Spring Boot 源码学习】HttpEncodingAutoConfiguration 详解
|
11月前
|
机器学习/深度学习 算法 测试技术
3天把Llama训成Mamba,性能不降,推理更快!
【10月更文挑战第7天】论文《Distilling and Accelerating Hybrid Models》提出了一种将大型Transformer模型高效转化为线性RNN模型的新方法,通过重用注意力层中的线性投影权重,实现性能不降甚至提升。研究通过多阶段蒸馏方法训练模型,包括渐进蒸馏、监督微调和定向偏好优化,确保了模型在标准聊天基准测试中的优异表现。实验结果表明,蒸馏后的混合模型在多个任务上与原模型及同类模型相比,表现出色或更优。然而,该方法仍需大量计算资源,并在特定任务上可能存在性能差距。
128 1
|
前端开发 JavaScript API
reactAPI讲解以及注意事项
reactAPI讲解以及注意事项
74 2
|
设计模式 Go
Go语言实现设计模式之适配器模式
适配器模式是一种常用的设计模式,用于将一个类的接口转换成客户端所期望的另一种接口。本文将详细介绍适配器模式的概念和原理,并使用Go语言实现一个示例,以帮助读者更好地理解该设计模式的应用。
335 0
|
Rust 数据可视化 安全
【番外篇】Rust环境搭建+基础开发入门+Rust与.NET6、C++的基础运算性能比较
突然想打算把Rust作为将来自己主要的副编程语言。当然,主语言还是C#,毕竟.NET平台这么强大,写起来就是爽。缘起:之前打算一些新的产品或者新的要开发的东西,由于没有历史包袱,就想重新选型一下,在.NET平台(C#语言)、Golang、Rust里面进行选择一个。
445 0
【番外篇】Rust环境搭建+基础开发入门+Rust与.NET6、C++的基础运算性能比较
v-for遍历对象、数组
v-for遍历对象、数组
154 0
|
C语言
【C 语言】数组 ( 数组相关地址 | 数组首元素地址 | 数组地址 )
【C 语言】数组 ( 数组相关地址 | 数组首元素地址 | 数组地址 )
326 0
【C 语言】数组 ( 数组相关地址 | 数组首元素地址 | 数组地址 )
|
消息中间件 云安全 运维
我们找阿里云资深技术专家李响聊了聊开源和云原生
在第十五届“开源中国开源世界”高峰论坛上,阿里云资深技术专家、etcd 创始人、CNCF TOC(Technical Oversight Committee,简称TOC)李响荣获2020中国开源杰出人物贡献奖。恭喜李响!
793 0
我们找阿里云资深技术专家李响聊了聊开源和云原生
|
Oracle 安全 关系型数据库
小编教你Oracle数据库ORA-28002错误原因及解决办法
  近期小编在开发api接口时,调试中接口返回ORA-28002错误,看前缀知道是Oracle返回的错误信息,随查了下Oracle相关文档。在此把解决方案分享给有需要的朋友。在oracle database 11g中,默认在default概要文件中设置了“PASSWORD_LIFE_TIME=180天”所导致。密码过期后,业务进程连接数据库异常,影响业务使用。数据库密码过期后,业务进程一旦重启会提示连接失败。注:Oracle 11g启动参数resource_limit无论设置为false还是true,密码有效期都是生效的,所以必须通过以下方式进行修改:
725 0