学习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 相关文章推荐
JQuery 学习笔记 选择器之五
Jul 23 Javascript
js操作时间(年-月-日 时-分-秒 星期几)
Jun 20 Javascript
Javascript alert消息换行的方法
Aug 07 Javascript
同域jQuery(跨)iframe操作DOM(示例代码)
Dec 13 Javascript
一个炫酷的Bootstrap导航菜单
Dec 28 Javascript
js数组实现权重概率分配
Sep 12 Javascript
基于Vuejs的搜索匹配功能实现方法
Mar 03 Javascript
Vue入门学习笔记【基本概念、对象、过滤器、指令等】
Apr 13 Javascript
详解微信小程序开发聊天室—实时聊天,支持图片预览
May 20 Javascript
thinkjs微信中控之微信鉴权登陆的实现代码
Aug 08 Javascript
解决vue-router 二级导航默认选中某一选项的问题
Nov 01 Javascript
基于javascript处理二进制图片流过程详解
Jun 08 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
轻松修复Discuz!数据库
2008/05/03 PHP
php遍历数组的4种方法总结
2014/07/05 PHP
PHP-CGI远程代码执行漏洞分析与防范
2017/05/07 PHP
PHP策略模式定义与用法示例
2017/07/27 PHP
laravel添加前台跳转成功页面示例
2019/10/22 PHP
js 无提示关闭浏览器页面的代码
2010/03/09 Javascript
JS 实现图片直接下载示例代码
2013/07/22 Javascript
jQuery:delegate中select()不起作用的解决方法(实例讲解)
2014/01/26 Javascript
Javascript连接多个数组不用concat来解决
2014/03/24 Javascript
javascript实现类似百度分享功能的方法
2015/07/27 Javascript
jQuery实现二级下拉菜单效果
2016/01/05 Javascript
jquery实现全选和全不选功能效果的实现代码【推荐】
2016/05/05 Javascript
详解js中call与apply关键字的作用
2016/11/21 Javascript
JS设计模式之单例模式(一)
2017/09/29 Javascript
vue checkbox 全选 数据的绑定及获取和计算方法
2018/02/09 Javascript
vue实现打印功能的两种方法
2018/09/07 Javascript
nodejs初始化init的示例代码
2018/10/10 NodeJs
vue.js中使用echarts实现数据动态刷新功能
2019/04/16 Javascript
js实现简单点赞操作
2020/03/17 Javascript
浅析TypeScript 命名空间
2020/03/19 Javascript
js节流防抖应用场景,以及在vue中节流防抖的具体实现操作
2020/09/21 Javascript
基于Django模板中的数字自增(详解)
2017/09/05 Python
python检测空间储存剩余大小和指定文件夹内存占用的实例
2018/06/11 Python
对Python的zip函数妙用,旋转矩阵详解
2018/12/13 Python
python pillow模块使用方法详解
2019/08/30 Python
python烟花效果的代码实例
2020/02/25 Python
pycharm设置python文件模板信息过程图解
2020/03/10 Python
更新升级python和pip版本后不生效的问题解决
2020/04/17 Python
详解pandas中利用DataFrame对象的.loc[]、.iloc[]方法抽取数据
2020/12/13 Python
雅萌 (YA-MAN) :日本美容家电领域的龙头企业
2017/05/12 全球购物
sealed修饰符是干什么的
2012/10/23 面试题
蔬菜基地的创业计划书
2014/01/06 职场文书
员工离职通知函
2015/04/25 职场文书
向雷锋同志学习倡议书
2015/04/27 职场文书
观后感的写法
2015/06/19 职场文书
Python面向对象之内置函数相关知识总结
2021/06/24 Python