Android设计模式之——策略模式

一、介绍

在软件开发中也常常遇到这样的情况:实现某一个功能可以有多种算法或者策略,我们根据实际情况选择不同的算法或者策略来完成该功能。例如,排序算法,可以使用插入排序、归并排序、冒泡排序等。

针对这种情况,一种常规的方法是将多种算法写在一个类中。例如,需要提供多种排序算法,可以将这些算法写到一个类中,每一个方法对应一个具体的排序算法:当然,也可以将这些排序算法封装在一个统一的方法中,通过if…else…或者case等条件判断语句来选择具体的算法。这两种实现方法我们都可以称为硬编码。然而,当很多个算法集中在一个类中时,这个类就会变得臃肿,这个类的维护成本会变高,在维护时也更容易引发错误。如果我们需要增加一种新的排序算法,需要修改封装算法类的源代码。这就明显违反了OCP原则和单一职责原则。

如果将这些算法或者策略抽象出来,提供一个统一的接口,不同的算法或者策略有不同的实现类,这样在程序客户端就可以通过注入不同的实现对象来实现算法或者策略的动态替换,这种模式的可扩展性、可维护性也就更高,也就是我们本节要说的策略模式。

简单来说就是,通常如果一个问题有多个解决方案时,最简单的就是利用if-else或者switch-case方式根据不同的情景选择不同的解决方案,但是这样耦合性太高 、代码臃肿、难以维护等。这时就可以使用策略模式来解决。

二、定义

策略模式定义了一系列的算法,并将每一个算法封装起来,而且使它们还可以相互替换。策略模式让算法独立于使用它的客户而独立变化。

三、使用场景

  • 针对同一类型问题的多种处理方式,仅仅是具体行为有差别时

  • 需要安全的封装多种同一类型的操作时

  • 出现同一抽象类有多个子类,而又需要使用if-else或者switch-case来选择具体子类时

四、策略模式的UML类图

UML类图:

这里写图片描述

  • Context:用来操作策略的上下文环境。

  • Stragety:策略的抽象。

  • ConcreteStrategyA、ConcreteStrategyB:具体的策略实现。

五、简单实现

需求:计算图书价格,初级会员没有折扣,中级会员打9折,高级会员打8折。如果一般写法,应该是if-else判断他是什么级别的会员,在计算相应的折扣。下面使用策略模式来进行实现。

抽象折扣类:

public interface MemberStrategy {/*** 计算图书的价格* @param booksPrice    图书的原价* @return    计算出打折后的价格*/public double calcPrice(double booksPrice);
}

初级会员折扣类:

public class PrimaryMemberStrategy implements MemberStrategy{/*** 初级会员折扣*/@Overridepublic double calcPrice(double booksPrice) {System.out.println("对于初级会员的没有折扣");return booksPrice;}
}

中级会员折扣类:

public class IntermediateMemberStrategy implements MemberStrategy{/*** 中级会员折扣*/@Overridepublic double calcPrice(double booksPrice) {System.out.println("对于中级会员的折扣为10%");return booksPrice * 0.9;}
}

高级会员折扣类:

public class AdvancedMemberStrategy implements MemberStrategy{/*** 高级会员折扣*/@Overridepublic double calcPrice(double booksPrice) {System.out.println("对于高级会员的折扣为20%");return booksPrice * 0.8;}
}

价格类:

public class Price {//持有一个具体的策略对象private MemberStrategy strategy;/*** 构造函数,传入一个具体的策略对象* @param strategy    具体的策略对象*/public Price(MemberStrategy strategy){this.strategy = strategy;}/*** 计算图书的价格* @param booksPrice    图书的原价* @return    计算出打折后的价格*/public double quote(double booksPrice){return this.strategy.calcPrice(booksPrice);}
}

客户端:

public class Client {public static void main(String[] args) {//选择并创建需要使用的策略对象MemberStrategy strategy1 = new AdvancedMemberStrategy();//创建环境Price price = new Price(strategy1);//计算价格double quote = price.quote(300);System.out.println("图书的最终价格为:" + quote);}}

结果:

对于高级会员的折扣为20%
图书的最终价格为:240.0

六、策略模式和工厂模式的区别

这里写图片描述

七、Android源码中的策略模式实现

随着技术的发展,工程师们已经越来越重视用户体验、用户交互。因此,动画成了很多应用中必不可少的部分,一个简单的引导页面也要做成动画的效果,一个按钮的隐藏也需要加入淡入淡出的动画效果。动画的实现原理就是在短时间内快速的进行画面切换,这个切换频率需要达到人眼感觉不出卡顿,例如标准的电影是24帧/秒。在比较流畅时,Android上的动画能够达到60帧/秒,人眼基本看不出间隔,所以,在我们看到这个动画就非常流畅。

单纯是动画还不足以满足我们的需求,在动画执行的过程中,我们还需要一些动态效果,这有点类似于电影的慢镜头,有时候我们需要它慢一点,有时候需要快一点,这样动画也变得灵动起来。这些动态效果就是通过插值器(TimeInterpolator)实现的,我们只需要对Animation对象设置不同的插值器就可以实现不同的动态效果。

LinearInterpolator、AccelerateInterpolator、CycleInterpolator等实现Interpolator,通过getInterpolator(float input)获取当前的时间百分比,以此来计算动画的属性值。

八、总结

策略模式主要用来分离算法,在相同的行为抽象下有不同的具体实现策略。这个模式很好地演示了开闭原则,也就是定义抽象,注入不同的实现,从而达到很好的可扩展性。

优点:

  • 结构清晰明了、使用简单直观。

  • 耦合度相对而言较低,扩展方便。

  • 操作封装也更为彻底,数据更为安全。

缺点:

  • 随着策略的增加,子类也会变得繁多。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/447024.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

密码学在区块链隐私保护中的应用学习

身份隐私保护技术 混淆服务 混淆服务的目的在于混淆消息双方的联系(如 图 2 所示)。当发送方需要告知接收方消息 M 时, 它会首先用接收方的公钥 KB 加密 M,并在密文后 附带真实接收地址 R。为了借助第三方(图 2 中的…

值类型和引用类型的区别

一、定义 引用类型表示你操作的数据是同一个,也就是说当你传一个参数给另一个方法时,你在另一个方法中改变这个变量的值,那么调用这个方法是传入的变量的值也将改变。 值类型表示复制一个当前变量传给方法,当你在这个方法中改变…

面向区块链的高效物化视图维护和可信查询论文学习

物化视图介绍 如何维护物化视图仍旧是一个开放问题.在关系数据库中,增量刷新的物化视图维护策略可划分为立即维护和延迟维护两大类.立即维护策略的优点是实现较为简单,在单数据源下不 存在一致性问题;然而该策略将物化视图维护过程嵌入到更新事务之中,延长了更新事务的提交时间…

密码学数字信封的介绍

对称密码和非对称密码 对称密码:加解密运算非常快,适合处理大批量数据,但其密码的分发与管理比较复杂非对称密码:公钥和私钥分离,非常适合密钥的分发和管理 数字信封的定义 如果将对称密码算法和非对称密码算法的优点…

Android设计模式之——状态模式

一、介绍 状态模式中的行为是由状态来决定的,不同的状态下有不同的行为。状态模式和策略模式的结构几乎完全一样,但它们的目的、本质却完全不一样。状态模式的行为是平行的、不可替换的,策略模式的行为是彼此独立、可相互替换的。用一句话来…

Android设计模式之——责任链模式

一、介绍 责任链模式(Iterator Pattern),是行为型设计模式之一。什么是”链“?我们将多个节点首尾相连所构成的模型称为链,比如生活中常见的锁链,就是由一个个圆角长方形的铁环串起来的结构。对于链式结构…

目前基于区块链的档案防篡改系统的设计如何实现防篡改

架构设计图 分析 为了保障档案数据的安全性和隐私性,存储档案附件和档案属性存储加密存储在私有IPFS集群,档案的IPFS地址和数字指纹存储在私有区块链上。公有区块链定期存储和检查私有区块链最新不可逆区块的高度和哈希值,以保障私有区块链上…

IPFS的文件存储模式

IPFS是如何进行文件存储的 IPFS采用的索引结构是DHT(分布式哈希表),数据结构是MerkleDAG(Merkle有向无环图) DHT(分布式哈希表) 参考链接MerkleDAG(Merkle有向无环图) 参考链接MerkleDAG功能…

Android设计模式之——解释器模式

一、介绍 解释器模式(Interpreter Pattern)是一种用的比较少的行为型模式,其提供了一种解释语言的语法或表达式的方式,该模式定义了一个表达式接口,通过该接口解释一个特定的上下文。在这么多的设计模式中&#xff0c…

在Docker里面安装Ubuntu,并且使用ssh进行连接

创建Ubuntu镜像 1,拉取Ubuntu系统的镜像 docker pull ubuntu2、查看拉取是否成功 docker images3,运行容器 docker run --name 新建的容器的名字 -ti -v /AAA:/BBB -d -p 3316:22 ubuntu(这个是镜像的名字)宿主机根目录中的AAA文件夹就映射到了容器…

Android设计模式之——命令模式

一、介绍 命令模式(Command Pattern),是行为型设计模式之一。命令模式相对于其他的设计模式来说并没有那么多的条条框框,其实它不是一个很”规范“的模式,不过,就是基于这一点,命令模式相对于其…

Android设计模式之——观察者模式

一、介绍 观察者模式是一个使用率非常高的模式,它最常用的地方是GUI系统、订阅——发布系统。因为这个模式的一个重要作用就是解耦,将被观察者和观察者解耦,使得它们之间的依赖性更小,甚至做到毫无依赖。以GUI系统来说&#xff0…

Android设计模式之——备忘录模式

一、介绍 备忘录模式是一种行为模式,该模式用于保存对象当前状态,并且在之后可以再次恢复到此状态,这有点像我们平时说的”后悔药“。备忘录模式实现的方式需要保证被保存的对象状态不能被对象从外部访问,目的是为了保护好被保存…

C++ using的三种使用策略以及具体的用法

Using的使用方法 1,命名空间的使用 为了防止代码冲突,都会使用到命名空间。假设这样一种情况,当一个班上有两个名叫 Zara 的学生时,为了明确区分他们,我们在使用名字之外,不得不使用一些额外的信息&#…

Android设计模式之——迭代器模式

一、介绍 迭代器模式(Iterator Pattern)又称为游标(Cursor)模式,是行为型设计模式之一。迭代器模式算是一个比较古老的设计模式,其源于对容器的访问,比如Java中的List、Map、数组等&#xff0c…

Android设计模式之——模板方法模式

一、介绍 在面向对象开发过程中,通常会遇到这样的一个问题,我们知道一个算法所需的关键步骤,并确定了这些步骤的执行顺序,但是,某些步骤的具体实现是未知的,或者说某些步骤的实现是会随着环境的变化而改变…

Android设计模式之——访问者模式

一、介绍 访问者模式是一种将数据操作与数据结构分离的设计模式,它是《设计模式》中23种设计模式中最复杂的一个,但它的使用频率并不高,正如《设计模式》的作者GOF对访问者模式的描述:大多数情况下,你不需要使用访问者…

Android设计模式之——中介者模式

一、介绍 中介者模式(Mediator Pattern)也称为调解者模式或调停者模式,Mediator本身就有调停者和调解者的意思。 在日常生活中调停者或调解者这个角色我们见得比较多的是“和事老”,也就是说调解两个有争端的人的角色&#xff0…

Java基础——虚拟机结构

一、Java平台结构图二、JVM、JRE和JDK关系JVM:Java Virtual Machine(Java虚拟机),负责执行符合规范的Class文件 JRE: Java Runtime Environment (java运行环境),包含JVM和类库 JDK&a…

C++:MAC安装Boost库文件并且使用CLion开发

boost的filestem库 C在17版本的标准库中引入了一个filesystem库,用来处理文件路径,以及文件访问。很多编译器对filesystem库的支持还不是很好。为了解决这个问题,可以临时使用boost::filesystem来替代。其实C17标准中的filesystem库就是从bo…