首页 > 其他分享 >策略模式

策略模式

时间:2022-11-29 21:22:41浏览次数:38  
标签:策略 实现 代码 接口 飞行 模式 行为 鸭子

风带着万物全部飘散,可那飘散的不是万物,而是我的青春

一个简单的鸭子应用

使用简单继承的模式实现多个不同的鸭子实现类。

新需求 - 鸭子能飞

现在公司为了甩开其他竞争者,需要在应用中添加一个新需求,得让鸭子飞起来。

如图所示,只要在鸭子类中新增一个让鸭子飞的方法即可。

可怕的事情发生了

在公司的应用演示会上,有很多橡皮鸭在屏幕上飞来飞去。

造成这种问题提出现的原因:并不是所有的鸭子都会飞。

提示:

  • 对代码所做的局部修改,影响层面可不只是局部(会飞的橡皮鸭)

  • 当涉及到代码的维护时,为了“复用”代码而使用继承,结局并不完美

利用接口改造代码

fly()方法从超类中去取出来,放进一个Flyable接口,只有会飞的鸭子去实现这个飞的接口。

这种接口改造,确实可以实现目的。但是太笨了,完全不利于代码的复用与维护。如果项目后期需要你修改一下鸭子的飞行动作,那么你是不是要去每一个鸭子的实现类里进行修改。

Java接口不具有现实代码,所以继承接口无法实现代码的复用。这意味着:无论什么时候你需要修改其实现类的某一个行为,你都要往下追踪到实现类中进行修改。

我们要做的应该是,花费较少的时间重做代码,而让程序去做更酷的事情。

把问题归零

上面问题出现的原因,就是新需求来的时候,我们改动了系统中的某些部分,导致系统其他部分受到了影响。

所以,要解决这个问题,就是要把这两部分分开,各自封装处理。

即:

设计原则:

找到应用中可能需要变化之处,把它们独立出来,不要和那些不需要变化的代码混在一起。

分开变化和不会变化的部分

找出应用中哪些是不变的,哪些是变化的。

不变的:swim()display() 基本上所有的鸭子都会

会变化的:fly()quack() 不同的鸭子叫声和飞行动作不一样

把这两部分分开

设计鸭子的行为

好的代码是非常有弹性的,就是因为一开始代码没有弹性,才走到现在这条路上的。

如果我们现在需要生产一个新的绿鸭头实例,并指定特定“类型”的飞行行为给它。干脆顺便让鸭子的行为可以动态地改变好了。换句话说,我们应该在鸭子类中包含设定行为的方法,这样就可以在“运行时”动态地“改变”绿鸭头的飞行行为。

要实现这个目标,就需要用到下面的设计原则:

针对接口编程,而不是针对实现编程。

  • 以往的做法:行为来自Duck超类的具体实现,或是继承某个接口并由子类自行实现而来。这两种做法都是依赖于“实现”,我们被实现绑定死死的,要更改行为,就要去实现类里进行代码的修改。

  • 针对接口编程:Duck的子类将使用接口(FlyBehaviorQuackBehavior)所表示行为,所以实际的“实现”不会被绑死在鸭子的子类中。(换句话说,特定的具体行为编写在实现了FlyBehaviorQuackBehavior的类中)。

    • 这样做的好处,后面新增一些新的行为,就不会影响到之前的代码,只需要在接口上进行扩展即可。而且这种方式,鸭子类就不再需要知道行为的具体实现细节,只需要调用接口的方法即可。

整合鸭子的行为

关键在于,鸭子现在会将飞行和呱呱叫行为“委托”别人处理,而不是使用定义在Duck类或其子类的呱呱叫和飞行行为。

每只鸭子都会引用实现QuackBehavior接口对象,鸭子对象不亲自处理呱呱叫和飞行行为,而是委托给代理接口去处理。

封装行为的大局观

核心:不再把鸭子的行为说成是“一组行为”,现在开始把行为想成是“一族算法”。

“有一个”可能比“是一个”更好

每一个鸭子都有一个FlyBehavior和一个QuackBehavior,好将飞行和呱呱叫行为委托给它们代为处理。当你将两个类结合起来使用,这就叫组合。

这种组合做法与“继承”不同的地方在于,鸭子行为不是继承来的,而是和适当的行为对象“组合”来的。

这就是第三个设计原则:

多用组合,少用继承。

使用组合建立系统具有很大的弹性,不仅可将算法族封装成类,更可以“在运行时动态地改变行为”,只要组合的行为对象符合正确的接口标准即可。

总结

这就是策略模式(Strategy Pattern),策略模式定义了算法族,分别封装起来,让它们之间可以互相替换,此模式让算法的变化独立于使用算法的客户。

 

标签:策略,实现,代码,接口,飞行,模式,行为,鸭子
From: https://www.cnblogs.com/l12138h/p/16936757.html

相关文章

  • 设计模式之解释器模式
    文法规则和抽象语法树解释器模式描述了如何为简单的语言定义一个文法,如何在该语言中表示一个句子,以及如何解释这些句子。在正式分析解释器模式结构之前,先来学习如何表示一......
  • (十六)状态模式
    1概述状态模式(State),当一个对象的内在状态改变时允许改变其行为,这个对象看起来像是改变了其类。状态模式主要解决的是当控制一个对象状态转换的条件表达式过于复杂时的......
  • C#设计模式读书笔记之设计模式的设计原则
    设计模式的设计原则:(重要性从上往下排列)开闭原则:对扩展开放,对修改关闭依赖倒转原则:高层模块不应该依赖底层模块,它们都应该依赖抽象;要针对抽象层编程,而不要针对具体类编程。......
  • Docker使用Calico网络模式配置及问题处理
    一.Calico介绍Calico是一种容器之间互通的网络方案,在虚拟化平台中,比如OpenStack、Docker等都需要实现workloads之间互连,但同时也需要对容器做隔离控制,就像在Internet中的......
  • 安卓设计模式演变之经典三层模型(MVC/MVP/MVVM)
    转载请标明出处!先看代码demo再回看文章效果最佳!目录​​一mvc​​​​1.1概述​​​​1.2 作用流程​​​​1.3 现状​​​​1.4致命弱点/缺点:​​​​1.5 代码Demo​......
  • Java内功修炼系列:代理模式及动态代理
    目录​​一代理模式​​​​1.1简介​​​​1.2代理模式角色定义​​​​二静态代理​​​​2.1介绍和实例​​​​2.2静态代理的缺点​​​​三动态代理​​​​3.1......
  • 每天一点基础K8S--K8S中的调度策略--节点亲和性、反亲和性
    K8S中的调度策略--节点亲和性、pod亲和性上面实验了nodeName和nodeSelector,其中,nodeName是通过节点的名称进行区分,在一些特定场景下还是很有用的,如果将节点调度到某一高性......
  • 如何解决win10系统睡眠模式及断网的情况?
    由于测试需求,所以临时在win10上面搭建了一套web系统。但是发现了一个大问题,每隔一段时间,网络就不通了。后面发现原来是系统自动休眠把网卡关闭了。解决方法如下:1.禁止关闭网......
  • 拓端tecdat|上海无印良品地理空间分布特征与选址策略可视化研究
    作者:HerbertHu项目挑战无印良品,是指“没有名字的优良商品”,于1980年诞生于日本,主推服装、生活杂货、食品等各类优质商品。2005年,无印良品进入中国市场,产品注重纯朴、简洁......
  • 备忘录模式
    大家有没有看过尼古拉斯凯奇主演过的《NEXT》(《预见未来》)?尼古拉斯凯奇饰演一个可以预视并且扭转未来的人,其中一个情节很是让人心动——男女主角见面的那段情节:。。。。。。......