Markdown版本笔记 我的GitHub首页 我的博客 我的微信 我的邮箱
MyAndroidBlogs baiqiantao baiqiantao bqt20094 baiqiantao@sina.com

目录

策略模式

简介

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

使用这个模式来将一组算法封装成一系列对象,通过传递这些对象可以灵活的改变程序的功能。

使用场景

  • 针对同一类型问题的多种处理方式,仅仅是具体行为有差别时
  • 需要安全地封装多种同一类型的操作时
  • 出现同一抽象类有多个子类,而又需要通过if-else或者switch-case来选择具体的子类时

使用例子:

Android中属性动画的时间差值器分为线性差值器、加速减速差值器等,这些差值器里面就用到了策略模式来隔离不同的动画速率计算算法。


在软件开发中也常常遇到类似的情况,实现某一个功能有多种算法或者策略,我们可以根据环境或者条件的不同选择不同的算法或者策略来完成该功能,如查找、排序等。

一种常用的方法是硬编码,在一个类中如需要提供多种查找算法,可以将这些算法写到一个类中,在该类中提供多个方法,每一个方法对应一个具体的查找算法;当然也可以将这些查找算法封装在一个统一的方法中,通过if…else或者switch等条件判断语句来进行选择。

这两种实现方法我们都可以称之为硬编码,如果需要增加一种新的查找算法,需要修改封装算法类的源代码。更换查找算法,也需要修改客户端调用代码。

在这个算法类中封装了大量查找算法,该类代码较复杂,维护较为困难。

如果我们将这些策略包含在客户端,这种做法更不可取,将导致客户端程序庞大而且难以维护,如果存在大量可供选择的算法时问题将变得更加严重。


模式的组成

  • 环境类(Context):用一个ConcreteStrategy对象来配置。维护一个对Strategy对象的引用。可定义一个接口来让Strategy访问它的数据。
  • 抽象策略类(Strategy):定义所有支持的算法的公共接口。Context使用这个接口来调用某ConcreteStrategy定义的算法。
  • 具体策略类(ConcreteStrategy):以Strategy接口实现某具体算法。

总结

  • 策略模式主要用来分离算法,在相同的行为抽象下有不同的具体实现策略。
  • 策略模式很好地展示了开闭原则,也就是定义抽象,注入不同的实现,从而达到很好的扩展性
  • 当我们在实现一个功能时遇到很多if-else或是switch-case的时候就可以考虑下这里是不是可以用策略模式了

案例

下面我们以计算不同交通工具的车费来简单看看策略模式的实现

首先抽象出计算车费的操作,因为不同的策略最后都会计算车费并返回结果

public interface CalculateStragety {
int calculatePrice(int km); //根据公里数计算价格
}

然后我们分别实现具体的策略,比如计算公交车的车费的策略

public class BusStragety implements CalculateStragety {

    @Override
public int calculatePrice(int km) {
return 2; //省略具体的算法
}
}

再加一个出租车的车费计算策略

public class TaxiStragety implements CalculateStragety {
@Override
public int calculatePrice(int km) {
return 10 + km * 2; //省略具体的算法
}
}

然后我们看看怎么根据需要注入不同的策略,并把具体的计算委托给注入的策略

public class TrafficCalculator {
private CalculateStragety mCalculateStragety; public void setCalculateStragety(CalculateStragety calculateStragety) {
mCalculateStragety = calculateStragety; //根据需要注入相应的策略
} public int calculatePrice(int km) {
return mCalculateStragety.calculatePrice(km); //把具体的计算委托给注入的策略
}
}

测试

class Test {
public static void main(String[] args) {
TrafficCalculator trafficCalculator = new TrafficCalculator();
trafficCalculator.setCalculateStragety(new BusStragety());
trafficCalculator.calculatePrice(66);
}
}

在上面的例子中我们通过在TrafficCalculator中动态注入计算公交车车费的策略来计算公交车费,当然我们也可以计算出租车费,只需要把注入的策略改为出租车车费计算策略就可以了。

2016-04-21

ViewPage 大圣归来 原生示例的更多相关文章

  1. ButterKnife 8.2.1 大圣归来

    零.前言 ButterKnife是一个视图注入的框架,主要帮我们解决无脑的findViewById.设置监听事件等等体力劳动. 一.引入 好消息是ButterKnife终于使用apt生成代码了,首先在 ...

  2. 大圣画廊v0.2(2015.7.17)

    0.2版本号加入的功能 以tag分类图片 美化.添加瀑布流效果 添加tag页和单张图片页 添加公布图片页 以下是具体解释. 每添加一个功能,都要从模型.模板,视图,路由四个方面一一改动. 模型:添加t ...

  3. Java类初始化顺序,大神3个示例带你躺坑。。

    最近发现微信群里面有些群友在讨论类的初始化顺序,如类的静态变量.成员变量.静态代码块.非静态代码块.构造器,及继承父类时,它们的初始化顺序都是怎样的,下面我通过例子来说明这个情况,以免被人误导. 示例 ...

  4. JS原生示例 案例 学习

    写在前面 原生JS是原理,框架是迎合业务需求的重要关键工具 本文是整理工作及学习中理解的基础和难点,便于多方位理解功能模块整合和使用 不定期更新 行文仓促,文中有错误在所难免,欢迎诸位指正 trans ...

  5. 5大最新云原生镜像构建工具全解析,3个来自Google,你了解几个?

    1云原生大背景下的镜像构建在分享开始,我想先跟大家简单聊一下云原生,可能不会详细展开,而是带领大家了解一下云原生对镜像构建方面的影响.第一,在接触云原生相关的技术时,无论是要解决开发.测试环境的问题, ...

  6. Poco::JSON::Array 中object 设置preserveInsertionOrder 时,stringify出错-->深入解析

    在使用poco version 1.6.0时 Poco::JSON::Array 在object  设置preserveInsertionOrder =true 时 调用 array.stringif ...

  7. R语言——七月

    这两个月没有写什么代码.也没做什么大项目,基本就是对以前写的那个用ggplot2可视化数据的项目做一些增增补补,大部分技术难关都在ggplot2和R语言EXCEL处理这里解决并总结了.然后业余帮人修改 ...

  8. poco json 中文字符,抛异常JSON Exception -->iconv 转换 备忘录。

    起因 最近linux服务器通信需要用到json. jsoncpp比较出名,但poco 1.5版本以后已经带有json库,所以决定使用poco::json(linux 上已经用到了poco这一套框架). ...

  9. 让复杂Json数据和对象自由转换 --- Gson

    Gson是谷歌用于对Json操作的库,里面有着强大而又方便的功能,最常用的就是 fromJson():将json数据转化为对象: toJson():将对象转化为json数据! 对于普通的json数据使 ...

随机推荐

  1. 获取fragment中对应的控件的写法

    getActivity().findViewById(id);//用来关联activity中加载的控件id

  2. nginx 伪静态大于10个参数 $10

    伪静态大于10个参数   会解析成 $1   与 0 参考:http://zhidao.baidu.com/link?url=kT2tp8ARhIZsrt4XF3LdzjkEq0QTIbvhOj9Ck ...

  3. a便签 rel属性改变链接打开页面的方式

    <body> XHTML: <a href="http://www.baidu.com" rel="external">Baidu &l ...

  4. flvplayer.swf flv视频播放器使用方法

    今天由于网页上要加入一个视频文件,就研究了一下flv视频播放器flvplayer.swf      :   关于SewisePlayer  插件 演示例子链接   一.直接在html文件中加载: &l ...

  5. 移动H5前端性能优化指南[托尼托尼研究所]

    概述 1. PC优化手段在Mobile侧同样适用2. 在Mobile侧我们提出三秒种渲染完成首屏指标3. 基于第二点,首屏加载3秒完成或使用Loading4. 基于联通3G网络平均338KB/s(2. ...

  6. GitHub 入门

    1. CentOS 安装 Github. # sudo yum install skynet 安装之后查看一下版本. # git --version 2. 注册 Github 账号,登录后阅读 Git ...

  7. Chapter 2. OpenSSL的安装和配置学习笔记

    Chapter 2. OpenSSL的安装和配置学习笔记 2.1 在linux上面安装OpenSSL我还是做点No paper事情比较在行,正好和老师的课程接轨一下.以前尝试过在Windows上面安装 ...

  8. Matlab 数理统计

    1.离散随机分布 超几何分布:M:产品总数;K:次品数;N:抽样数. hygepdf(X, M,K,N):计算超几何分布的密度. 例:hygepdf(1,10,1,3),执行结果为ans=0.3000 ...

  9. Libpcap

    http://www.ibm.com/developerworks/cn/linux/l-libpcap/ http://www.linuxdevcenter.com/pub/a/linux/2003 ...

  10. MySQL AB复制

    http://tonychiu.blog.51cto.com/656605/326541