博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
浅析 JavaScript 链式调用
阅读量:4575 次
发布时间:2019-06-08

本文共 2657 字,大约阅读时间需要 8 分钟。

对$函数你已经很熟悉了。它通常返回一个html元素或一个html元素的集合,如下:

function$(){    var elements = [];    for(vari=0,len=arguments.length;i

 

但是,如果把这个函数改造为一个构造器,把那些元素作为数组保存在一个实例属性中,并让所有定义在构造器函数的prototype属性所指对象中的方法都返回用以调用方法的那个实例的引用,那么它就具有了链式调用的能力。我首先需要把这个$函数改为一个工厂方法,它负责创建支持链式调用的对象。这个函数应该能接受元素数组形式的参数,以便我们能够使用与原来一样的公用接口。

(function(){    //use private class      function _$(els){        this.elements = [];         for(vari=0,len=els.length;i

 

由于所有对象都会继承其原型对象的属性和方法,所以我们可以让定义在原型对象中的那几个方法都返回用以调用方法的实例对象的引用,这样就可以对那些方法进行链式调用。想好这一点,我们现在就动手在_$这个私用构造函数的prototype对象中添加方法,以便实现链式调用

(function(){    //use private class    function _$(els){        //..省略之前上面的代码    }    _$.prototype = {        each:function(fn){            for(var i=0,len=this.elements.length;i

 

但是如果某个库或者框架已经定义了一个$函数,那么我们的这个库会将其改写,有个简单的办法是在源码中为$函数另去一个名字。但是如果你是从一个现有的库获得的源码,那么每次代码库获取更新的版本后 你都得重新改名字,因此这个方案并不是很好。好的解决办法就是像下面一样添加一个安装器:

window.installHelper = function(scope, interface) {    scope[interface] = function() {      return new _$(arguments);    }  };

用户可以这样去使用:

installHelper(window, '$');$('example').show();

下面是一个更复杂的例子,它展示了如何把这种功能添加到一个事先定义好的命名对象中:

// Define a namespace without overwriting it if it already exists.window.com = window.com || {};com.example = com.example || {}; com.example.util = com.example.util || {};installHelper(com.example.util, 'get');(function() {  var get = com.example.util.get;  get('example').addEvent('click', function(e) {    get(this).addClass('hello');  });})();

 

 有时候把方法连起来并不是一个好主意。链式调用很适合于赋值器方法,但对于取值器的方法,你可能会希望他们返回你要的数据而不是返回this。不过,如果你把链式调用作为首要目标,希望所有方法的使用方式保持一致的话,那么变通的方法还是有的:你可以利用回调技术来返回所要的数据下面有两个例子:其中API类使用了普通的取值器(它中断了调用链),而API2类则使用了回调方法:

// Accessor without function callbacks: returning requested data in accessors.window.API = window.API || {};API.prototype = function() {  var name = 'Hello world';  // Privileged mutator method.  setName: function(newName) {    name = newName;    return this;  },  // Privileged accessor method.  getName: function() {    return name;  }}();// Implementation code.var o = new API;console.log(o.getName()); // Displays 'Hello world'.console.log(o.setName('Meow').getName()); // Displays 'Meow'.// Accessor with function callbacks.window.API2 = window.API2 || {};API2.prototype = function() {  var name = 'Hello world';  // Privileged mutator method.  setName: function(newName) {    name = newName;    return this;  },  // Privileged accessor method.  //通过把函数作为参数传入  getName: function(callback) {    callback.call(this, name);    return this;  }}();// Implementation code.var o2 = new API2;o2.getName(console.log).setName('Meow').getName(console.log);// Displays 'Hello world' and then 'Meow'.

 

转载于:https://www.cnblogs.com/huansky/p/5600438.html

你可能感兴趣的文章
从0开始学爬虫3之xpath的介绍和使用
查看>>
vim下正则表达式的非贪婪匹配
查看>>
一个python的计算熵(entropy)的函数
查看>>
spring源码学习——spring整体架构和设计理念
查看>>
模拟window系统的“回收站”
查看>>
报文格式【定长报文】
查看>>
RDLC报表钻取空白页问题
查看>>
多路电梯调度的思想
查看>>
jQuery-对Select的操作
查看>>
过滤器、监听器、拦截器的区别
查看>>
为什么要进行需求分析?通常对软件系统有哪些需求?
查看>>
一些模板
查看>>
jquery和dom元素相互转换
查看>>
放大的X--HDOJ-201307292012
查看>>
题目831-签到-nyoj-20140818
查看>>
百词斩-斩家秘籍
查看>>
Mysql主从配置,实现读写分离
查看>>
真事儿!——我们官网被全站拷贝了!
查看>>
抽象类及抽象方法
查看>>
Canvas基本绘画学习
查看>>