状态和行为:

所谓对象的状态,通常指的就是对象实例的属性的值;而行为指的就是对象的功能,再具体点说,行为大多可以对应到方法上。

状态模式的功能就是分离状态的行为,通过维护状态的变化,来调用不同状态对应的不同功能。也就是说,状态和行为是相关联的,它们的关系可以描述为:状态决定行为。

由于状态是在运行期被改变的,因此行为也会在运行期根据状态的改变而改变。

环境和状态处理对象:

在状态模式中,环境(Context)是持有状态的对象,但是环境(Context)自身并不处理跟状态相关的行为,而是把处理状态的功能委托给了状态对应的状态处理类来处理。

在具体的状态处理类中经常需要获取环境(Context)自身的数据,甚至在必要的时候会回调环境(Context)的方法,因此,通常将环境(Context)自身当作一个参数传递给具体的状态处理类。

看一个具体的实例:

1.State抽象类(当做接口):

var State = function () {

};

State.prototype.download = function () {
throw new Error("该方法必须被重载!");
}; State.prototype.pause = function () {
throw new Error("该方法必须被重载!");
}; State.prototype.fail = function () {
throw new Error("该方法必须被重载!");
}; State.prototype.finish = function () {
throw new Error("该方法必须被重载!");
};

2.Download类:(所谓的环境类,存有状态属性)

var Download = function () {
this.oState = new ReadyState(this);
}; Download.prototype.setState = function (oState) {
this.oState = oState;
}; // 对外暴露的四个公共方法,以便外部调用 Download.prototype.download = function () {
this.oState.download();
}; Download.prototype.pause = function () {
this.oState.pause();
}; Download.prototype.fail = function () {
this.oState.fail();
}; Download.prototype.finish = function () {
this.oState.finish();
};

3.6种不同的状态(每种状态都会调用Download类的改变状态的方法,进行状态切换)

(1)准备状态:

var ReadyState = function (oDownload) {
State.apply(this);
this.oDownload = oDownload;
}; ReadyState.prototype = new State(); ReadyState.prototype.download = function () {
this.oDownload.setState(this.oDownload.getDownloadingState());
// Ready以后,可以开始下载,所以设置了Download函数里的状态获取方法
console.log("Start Download!");
}; ReadyState.prototype.pause = function () {
throw new Error("还没开始下载,不能暂停!");
}; ReadyState.prototype.fail = function () {
throw new Error("文件还没开始下载,怎么能说失败呢!");
}; ReadyState.prototype.finish = function () {
throw new Error("文件还没开始下载,当然也不能结束了!");
};

(2)

var DownloadingState = function (oDownload) {
State.apply(this);
this.oDownload = oDownload;
}; DownloadingState.prototype = new State(); DownloadingState.prototype.download = function () {
throw new Error("文件已经正在下载中了!");
}; DownloadingState.prototype.pause = function () { this.oDownload.setState(this.oDownload.getDownloadPausedState());
console.log("暂停下载!");
}; DownloadingState.prototype.fail = function () { this.oDownload.setState(this.oDownload.getDownloadedFailedState());
console.log("下载失败!");
}; DownloadingState.prototype.finish = function () {
this.oDownload.setState(this.oDownload.getDownloadedState());
console.log("下载完毕!");
};

  

(3)

var DownloadPausedState = function (oDownload) {
State.apply(this);
this.oDownload = oDownload;
}; DownloadPausedState.prototype = new State(); DownloadPausedState.prototype.download = function () {
this.oDownload.setState(this.oDownload.getDownloadingState());
console.log("继续下载!");
}; DownloadPausedState.prototype.pause = function () {
throw new Error("已经暂停了,咋还要暂停呢!");
}; DownloadPausedState.prototype.fail = function () { this.oDownload.setState(this.oDownload.getDownloadedFailedState());
console.log("下载失败!");
}; DownloadPausedState.prototype.finish = function () {
this.oDownload.setState(this.oDownload.getDownloadedState());
console.log("下载完毕!");
};

  

(4)

var DownloadedState = function (oDownload) {
State.apply(this);
this.oDownload = oDownload;
}; DownloadedState.prototype = new State(); DownloadedState.prototype.download = function () {
this.oDownload.setState(this.oDownload.getDownloadingState());
console.log("重新下载!");
}; DownloadedState.prototype.pause = function () {
throw new Error("对下载完了,还暂停啥?");
}; DownloadedState.prototype.fail = function () {
throw new Error("都下载成功了,咋会失败呢?");
}; DownloadedState.prototype.finish = function () {
throw new Error("下载成功了,不能再为成功了吧!");
};

(5)

var DownloadFailedState = function (oDownload) {
State.apply(this);
this.oDownload = oDownload;
}; DownloadFailedState.prototype = new State(); DownloadFailedState.prototype.download = function () {
this.oDownload.setState(this.oDownload.getDownloadingState());
console.log("尝试重新下载!");
}; DownloadFailedState.prototype.pause = function () {
throw new Error("失败的下载,也不能暂停!");
}; DownloadFailedState.prototype.fail = function () {
throw new Error("都失败了,咋还失败呢!");
}; DownloadFailedState.prototype.finish = function () {
throw new Error("失败的下载,肯定也不会成功!");
};

4.首页:

<body>
<input type="button" value="开始下载" id="download_button" />
<input type="button" value="暂停" id="pause_button" />
<input type="button" value="重新下载" id="resume_button" />
<script> var oDownload = new Download();
$("#download_button").click(function () {
oDownload.download();
}); $("#pause_button").click(function () {
oDownload.pause();
}); $("#resume_button").click(function () {
oDownload.download();
});
</script>
</body>

  

  

  

JavaScript设计模式——状态模式的更多相关文章

  1. JavaScript设计模式 - 状态模式

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  2. javascript设计模式--状态模式(State)

    <!doctype html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  3. 【设计模式】Javascript设计模式——状态模式(行为型)

    注:这个模式是非常聪明的,很有点数学中组合的意思,现在,来看下这个模式是怎么个思想. 问题提出:假如某个操作有三种可能,分别为1,2,3,还可能是组合,比如先执行1,再执行2或者先执行2再执行3或者1 ...

  4. 14. 星际争霸之php设计模式--状态模式

    题记==============================================================================本php设计模式专辑来源于博客(jymo ...

  5. JavaScript设计模式 - 代理模式

    代理模式是为一个对象提供一个代用品或占位符,以便控制对它的访问 代理模式的用处(个人理解):为了保障当前对象的单一职责(相对独立性),而需要创建另一个对象来处理调用当前对象之前的一些逻辑以提高代码的效 ...

  6. [Head First设计模式]生活中学设计模式——状态模式

    系列文章 [Head First设计模式]山西面馆中的设计模式——装饰者模式 [Head First设计模式]山西面馆中的设计模式——观察者模式 [Head First设计模式]山西面馆中的设计模式— ...

  7. javascript 设计模式-----策略模式

    在<javascript设计模式>中,作者并没有向我们介绍策略模式,然而它却是一种在开发中十分常见的设计模式.最常见的就是当我们遇到一个复杂的表单验证的时候,常常需要编写一大段的if和el ...

  8. JAVA 设计模式 状态模式

    用途 状态模式 (State) 当一个对象的内在状态改变时允许改变其行为,这个对象看起来像是改变了其类. 状态模式是一种行为型模式. 结构

  9. 深入浅出设计模式——状态模式(State Pattern)

    模式动机 在很多情况下,一个对象的行为取决于一个或多个动态变化的属性,这样的属性叫做状态,这样的对象叫做有状态的 (stateful)对象,这样的对象状态是从事先定义好的一系列值中取出的.当一个这样的 ...

随机推荐

  1. Python 开发轻量级爬虫02

    Python 开发轻量级爬虫 (imooc总结02--爬虫简介) 爬虫简介 首先爬虫是什么?它是一段自动抓取互联网信息的程序. 什么意思呢? 互联网由各种各样的的网页组成,每一个网页都有对应的url, ...

  2. EL表达式中fn函数 (转载)

    JSTL 使用表达式来简化页面的代码,这对一些标准的方法,例如bean的getter/setter方法,请求参数或者context以及 session中的数据的访问非常方便,但是我们在实际应用中经常需 ...

  3. cordova android platform cordova build 遇到的问题

    版权声明:本文为博主原创文章,未经博主允许不得转载. 一.下载gradle-2.2.1-all.zip不成功,一直在下载,卡在这个downloading http://services.gradle. ...

  4. c# 类型拷贝

    /// <summary> /// 类 名:EntityHelper /// 类 说 明:实体操作方法类 /// : /// 创建时间:2013/8/12 /// </summary ...

  5. phpexcel生成excel并下载

    Loader::import('PHPExcel.Classes.PHPExcel'); // tp5中只需将phpexcel文件放入extend文件夹中,即可采用该方法引入,需要先 use thin ...

  6. 【leetcode】Number of Islands(middle)

    Given a 2d grid map of '1's (land) and '0's (water), count the number of islands. An island is surro ...

  7. #ifndef -摘自百度百科

    #ifndef 标识1 //判断"标识1"是否定义,如果被定义则返回假,如果没有被定义则返回真. /**********************************/ 语句1 ...

  8. 数据库的日志数据库(_log.ldf)文件太大,如何压缩

    DUMP TRANSACTION TCB WITH NO_LOGBACKUP LOG TCB WITH NO_LOGDBCC SHRINKDATABASE(TCB) 执行这三条语句就可以了,这里的TC ...

  9. php Internal Server Error

    Internal Server Error The server encountered an internal error or misconfiguration and was unable to ...

  10. Linux vmstat字段解析

    vmstat命令是最常见的Linux/Unix监控工具,可以展现给定时间间隔的服务器的状态值,包括服务器的CPU使用率,内存使用,虚拟内存交换情况,IO读写情况.这个命令是我查看Linux/Unix最 ...