学习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 动态生成表格示例代码
Dec 24 Javascript
jQuery toggleClass应用实例(附效果图)
Apr 06 Javascript
使用JavaScript的ActiveXObject对象检测应用程序是否安装的方法
Apr 15 Javascript
JS简单实现城市二级联动选择插件的方法
Aug 19 Javascript
javascript中alert()与console.log()的区别
Aug 26 Javascript
jquery获取form表单input元素值的简单实例
May 30 Javascript
vue.js中$watch的用法示例
Oct 04 Javascript
Bootstrap导航简单实现代码
Mar 06 Javascript
angular中ui calendar的一些使用心得(推荐)
Nov 03 Javascript
jQuery.validate.js表单验证插件的使用代码详解
Oct 22 jQuery
解决 viewer.js 动态更新图片导致无法预览的问题
May 14 Javascript
react的hooks的用法详解
Oct 12 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
PHP的类 功能齐全的发送邮件类
2006/10/09 PHP
关于php内存不够用的快速解决方法
2013/10/26 PHP
PHP CURL实现模拟登陆并上传文件操作示例
2020/01/02 PHP
JS中动态添加事件(绑定事件)的代码
2011/01/09 Javascript
js动态加载以及确定加载完成的代码
2011/07/31 Javascript
JavaScript中按位“异或”运算符使用介绍
2014/03/14 Javascript
js判断当前浏览器类型,判断IE浏览器方法
2014/06/02 Javascript
JS实现很实用的对联广告代码(可自适应高度)
2015/09/18 Javascript
JavaScript数组的一些奇葩行为
2016/01/25 Javascript
JavaScript获取客户端IP的方法(新方法)
2016/03/11 Javascript
Jquery EasyUI实现treegrid上显示checkbox并取选定值的方法
2016/04/29 Javascript
JavaScript鼠标事件,点击鼠标右键,弹出div的简单实例
2016/08/03 Javascript
JavaScript无阻塞加载和defer、async详解
2017/02/26 Javascript
AngularJS学习笔记之表单验证功能实例详解
2017/07/06 Javascript
深入剖析Node.js cluster模块
2018/05/23 Javascript
快速解决Vue项目在IE浏览器中显示空白的问题
2018/09/04 Javascript
JS实现倒计时图文效果
2018/11/17 Javascript
基于jsbarcode 生成条形码并将生成的条码保存至本地+源码
2020/04/27 Javascript
[03:01]完美盛典趣味短片 DOTA2年度最佳&拉胯英雄
2019/12/07 DOTA
python 专题九 Mysql数据库编程基础知识
2017/03/16 Python
python得到电脑的开机时间方法
2018/10/15 Python
Pandas读写CSV文件的方法示例
2019/03/27 Python
详解python函数的闭包问题(内部函数与外部函数详述)
2019/05/17 Python
PYQT5实现控制台显示功能的方法
2019/06/25 Python
Python列表删除元素del、pop()和remove()的区别小结
2019/09/11 Python
python用什么编辑器进行项目开发
2020/06/17 Python
Matplotlib.pyplot 三维绘图的实现示例
2020/07/28 Python
15个Pythonic的代码示例(值得收藏)
2020/10/29 Python
HTML5 CSS3新的WEB标准和浏览器支持
2009/07/16 HTML / CSS
给客户的道歉信
2014/01/13 职场文书
学生拾金不昧表扬信
2014/01/21 职场文书
个人课题方案
2014/05/08 职场文书
关于读书的演讲稿500字
2014/08/27 职场文书
电子银行业务授权委托书
2014/10/10 职场文书
先进集体事迹材料范文
2014/12/25 职场文书
2015年社区国庆节活动总结
2015/07/30 职场文书