学习JavaScript设计模式(代理模式)


Posted in Javascript onDecember 03, 2015

代理模式是为一个对象提供一个代用品或占位符,以便控制对它的访问
代理模式的用处(个人理解):为了保障当前对象的单一职责(相对独立性),而需要创建另一个对象来处理调用当前对象之前的一些逻辑以提高代码的效率、状态判断等。
代理模式中最常用的是虚拟代理缓存代理

一、虚拟代理
虚拟代理是把一些开销很大的对象,延迟到真正需要它的时候才去创建执行
示例: 虚拟代理实现图片预加载

// 图片加载函数
var myImage = (function(){
  var imgNode = document.createElement("img");
  document.body.appendChild(imgNode);

  return {
    setSrc: function(src) {
      imgNode.src = src;
    }
  }
})();

// 引入代理对象
var proxyImage = (function(){
  var img = new Image;
  img.onload = function(){
    // 图片加载完成,正式加载图片
    myImage.setSrc( this.src );
  };
  return {
    setSrc: function(src){
      // 图片未被载入时,加载一张提示图片
      myImage.setSrc("file://c:/loading.png");
      img.src = src;
    }
  }
})();

// 调用代理对象加载图片
proxyImage.setSrc( "http://images/qq.jpg");

示例: 虚拟代理合并HTTP请求
假设一个功能需要频繁的进行网络请求,这会造成相当大的开销,解决方案是通过一个代理函数来收集一段时间之内的请求,一次性发给服务器。
例如:做一个文件同步的功能,当我们选中一个文件时,就同步到另外一台备用服务器上

// 文件同步函数
var synchronousFile = function( id ){
  console.log( "开始同步文件,id为:" + id );
}
// 使用代理合并请求
var proxySynchronousFile = (function(){
  var cache = [], // 保存一段时间内需要同步的ID
    timer; // 定时器指针

  return function( id ){
    cache[cache.length] = id;
    if( timer ){
      return;
    }

    timer = setTimeout( function(){
      proxySynchronousFile( cache.join( "," ) ); // 2s 后向本体发送需要同步的ID集合
      clearTimeout( timer ); // 清空定时器
      timer = null;
      cache = []; // 晴空定时器
    },2000 );
  }
})();

// 绑定点击事件
var checkbox = document.getElementsByTagName( "input" );

for(var i= 0, c; c = checkbox[i++]; ){
  c.onclick = function(){
    if( this.checked === true ){
      // 使用代理进行文件同步
      proxySynchronousFile( this.id );
    }
  }
}

二、 缓存代理
缓存代理可以为一些开销大的运算结果提供暂时的存储,在下次运算时,如果传递进来的参数跟之前一致,则可以返回前面的运算结果。
示例: 为乘法、加法等创建缓存代理

// 计算乘积
var mult = function(){
  var a = 1;
  for( var i = 0, l = arguments.length; i < l; i++){
    a = a * arguments[i];
  }
  return a;
};
// 计算加和
var plus = function () {
 var a = 0;
  for( var i = 0, l = arguments.length; i < l; i++ ){
    a += arguments[i];
  }
  return a;
};
// 创建缓存代理的工厂
var createProxyFactory = function( fn ){
  var cache = {}; // 缓存 - 存放参数和计算后的值
  return function(){
    var args = Array.prototype.join.call(arguments, "-");
    if( args in cache ){ // 判断出入的参数是否被计算过
      console.log( "使用缓存代理" );
      return cache[args];
    }
    return cache[args] = fn.apply( this, arguments );
  }
};
// 创建代理
var proxyMult = createProxyFactory( mult ),
  proxyPlus = createProxyFactory( plus );

console.log( proxyMult( 1, 2, 3, 4 ) ); // 输出: 24
console.log( proxyMult( 1, 2, 3, 4 ) ); // 输出: 缓存代理 24
console.log( proxyPlus( 1, 2, 3, 4 ) ); // 输出: 10
console.log( proxyPlus( 1, 2, 3, 4 ) ); // 输出: 缓存代理 10

以上三个示例为大家详细介绍了javascript代理模式,希望对大家的学习有所帮助。

Javascript 相关文章推荐
JAVASCRIPT  THIS详解 面向对象
Mar 25 Javascript
JavaScript入门之基本函数详解
Oct 21 Javascript
封装好的javascript前端分页插件pagination
Jan 04 Javascript
原生JS实现首页进度加载动画
Sep 14 Javascript
jQuery实现倒计时(倒计时年月日可自己输入)
Dec 02 Javascript
Node.js连接postgreSQL并进行数据操作
Dec 18 Javascript
JavaScript数据结构之数组的表示方法示例
Apr 12 Javascript
vue.js删除动态绑定的radio的指定项
Jun 02 Javascript
vue中mint-ui的使用方法
Apr 04 Javascript
微信小程序授权登录解决方案的代码实例(含未通过授权解决方案)
May 10 Javascript
javascript实现倒计时效果
Feb 17 Javascript
关于uniApp editor微信滑动问题
Jan 15 Javascript
全面解析Bootstrap图片轮播效果
Dec 03 #Javascript
谈谈基于iframe、FormData、FileReader三种无刷新上传文件的方法
Dec 03 #Javascript
解决JavaScript数字精度丢失问题的方法
Dec 03 #Javascript
Javascript实现检测客户端类型代码封包
Dec 03 #Javascript
javascript学习小结之prototype
Dec 03 #Javascript
简单实现JS对dom操作封装
Dec 02 #Javascript
jQuery实现获取绑定自定义事件元素的方法
Dec 02 #Javascript
You might like
第九节--绑定
2006/11/16 PHP
discuz Passport 通行证 整合笔记
2008/06/30 PHP
PHP5.2中date()函数显示时间与北京时间相差8小时的解决办法
2009/05/28 PHP
PHP中使用GD库绘制折线图 折线统计图的绘制方法
2015/11/09 PHP
JS焦点图切换,上下翻转
2011/05/12 Javascript
基于jquery的大众点评,分类导航实现代码
2011/08/23 Javascript
详细介绍8款超实用JavaScript框架
2013/10/25 Javascript
jquery.uploadify插件在chrome浏览器频繁崩溃解决方法
2015/03/01 Javascript
jQuery解析XML文件同时动态增加js文件的方法
2015/06/01 Javascript
在JavaScript应用中使用RequireJS来实现延迟加载
2015/07/01 Javascript
js实现的二级横向菜单条实例
2015/08/22 Javascript
解决微信浏览器Javascript无法使用window.location.reload()刷新页面
2016/06/21 Javascript
JQuery实现图片轮播效果
2017/05/08 jQuery
JS实现图片预加载之无序预加载功能代码
2017/05/12 Javascript
JavaScript数组基于交换的排序示例【冒泡排序】
2018/07/21 Javascript
element el-input directive数字进行控制
2018/10/11 Javascript
vue-cli脚手架打包静态资源请求出错的原因与解决
2019/06/06 Javascript
微信内置开发 iOS修改键盘换行为搜索的解决方案
2019/11/06 Javascript
vue data变量相互赋值后被实时同步的解决步骤
2020/08/05 Javascript
[03:12]2016完美“圣”典风云人物:单车专访
2016/12/02 DOTA
python创建列表并给列表赋初始值的方法
2015/07/28 Python
一波神奇的Python语句、函数与方法的使用技巧总结
2015/12/08 Python
python编程进阶之异常处理用法实例分析
2020/02/21 Python
Pycharm激活方法及详细教程(详细且实用)
2020/05/12 Python
python导入库的具体方法
2020/06/18 Python
Python编写单元测试代码实例
2020/09/10 Python
详解css3使用transform出现字体模糊的解决办法
2020/10/16 HTML / CSS
亚马逊印度站:Amazon.in
2017/10/15 全球购物
PatPat阿根廷:妈妈们的购物平台
2019/05/30 全球购物
硕士研究生自我鉴定范文
2013/12/27 职场文书
2014学习优秀共产党员先进事迹思想汇报
2014/09/14 职场文书
2014年销售内勤工作总结
2014/12/01 职场文书
会议开幕词
2015/01/28 职场文书
钓鱼岛事件感想
2015/08/11 职场文书
【超详细】八大排序算法的各项比较以及各自特点
2021/03/31 Python
正确的理解和使用Django信号(Signals)
2021/04/14 Python