学习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不同页面传值的改进版
Sep 30 Javascript
Javascript hasOwnProperty 方法 &amp; in 关键字
Nov 26 Javascript
JQuery写动态树示例代码
Jul 31 Javascript
jquery五角星评分插件示例分享
Feb 21 Javascript
iframe实用操作锦集
Apr 22 Javascript
js图片自动轮播代码分享(js图片轮播)
May 06 Javascript
常常会用到的截取字符串substr()、substring()、slice()方法详解
Dec 16 Javascript
jquery Deferred 快速解决异步回调的问题
Apr 05 Javascript
bootstrap动态添加面包屑(breadcrumb)及其响应事件的方法
May 25 Javascript
VUE-cli3使用 svg-sprite-loader
Oct 20 Javascript
JSON的parse()方法介绍
Jan 31 Javascript
详解js 创建对象的几种方法
Mar 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
phpcms模块开发之swfupload的使用介绍
2013/04/28 PHP
PHP中遇到BOM、编码导致json_decode函数无法解析问题
2014/07/02 PHP
php+mysqli数据库连接的两种方式
2015/01/28 PHP
php 修改上传文件大小限制实例详解
2016/10/23 PHP
PHP数字前补0的自带函数sprintf 和number_format的用法(详解)
2017/02/06 PHP
PHP实现批量删除(封装)
2017/04/28 PHP
php+javascript实现的动态显示服务器运行程序进度条功能示例
2017/08/07 PHP
php7 错误处理机制修改实例分析
2020/05/25 PHP
JavaScript 中的replace方法说明
2007/04/13 Javascript
JS获得浏览器版本和操作系统版本的例子
2014/05/13 Javascript
Node.js编写组件的三种实现方式
2016/02/25 Javascript
总结几道关于Node.js的面试问题
2017/01/11 Javascript
jQuery学习之DOM节点的插入方法总结
2017/01/22 Javascript
javascript事件的传播基础实例讲解(35)
2017/02/14 Javascript
JavaScript原型继承_动力节点Java学院整理
2017/06/30 Javascript
vue-cli中安装方法(图文详细步骤)
2018/12/12 Javascript
[46:42]DOTA2-DPC中国联赛正赛 Aster vs Magma BO3 第二场 3月5日
2021/03/11 DOTA
Python中对元组和列表按条件进行排序的方法示例
2015/11/10 Python
Python利用flask sqlalchemy实现分页效果
2020/08/02 Python
Python使用pylab库实现绘制直方图功能示例
2018/06/01 Python
Python参数类型以及常见的坑详解
2019/07/08 Python
python 解决cv2绘制中文乱码问题
2019/12/23 Python
浅谈tensorflow模型保存为pb的各种姿势
2020/05/25 Python
Python多线程threading创建及使用方法解析
2020/06/17 Python
Python如何将字符串转换为日期
2020/07/31 Python
CSS3解决移动页面上点击链接触发色块的问题
2016/06/03 HTML / CSS
大学生的自我鉴定范文
2014/01/21 职场文书
酒店保安员岗位职责
2014/01/31 职场文书
保护动物的标语
2014/06/11 职场文书
国际贸易毕业生自荐书
2014/06/22 职场文书
普通党员对照检查材料
2014/09/24 职场文书
2015新年寄语(一句话)
2014/12/08 职场文书
师德先进个人材料
2014/12/20 职场文书
监理中标通知书
2015/04/16 职场文书
南京大屠杀观后感
2015/06/02 职场文书
初二英语教学反思
2016/02/15 职场文书