javascript 的bind/apply/call性能

javascript有两种使用频率非常高的三个内置的功能:bind/apply/call。许多技术是基于高点,这些功能实现。这三个功能被用来改变的功能运行环境.从而达到代码复用的目的。
先来所说bind函数, bind,函数通常有两个用途:

1. 创建新函数,指定函数的this指针。

name = 'global';
var obj1 = {name: 'foo'};
var showName = function() {
    console.log(this.name);
}
showName(); //global

var showObj = showName.bind(obj1);
showObj(); // foo

2. bind函数体现出偏函数的思维,能够有效降低匿名函数的使用,譬如,有一个接收用户不同请求并分发处理的模块:

//query: 请求參数
//config:不同请求的配置信息
function dispatcher(query, config) {
       var action = query.action;
       switch(action){
            case 'action1':{
            //....
                break;
            }
        }
}

dispatcher函数运行的操作都是相似的,仅仅是不同的用户请求须要不同的config配置信息。能够有例如以下做法:

function createDispatcher(config) {
    return function(query) {
        dispatcher(query, config);
    };
}

当然假设须要多个參数也能够这样搞:

function createDispatcher(config, ext) {
    //借用Array原型对象的slice函数把函数參数拷贝一份
    var args = Array.prototype.slice.call(arguments);
    return function (query) {
        var newArgs = args.push(query);
        dispatcher.apply(null, newArgs);
    }; 
}

假设通过bind来实现,能够这样搞:

function dispatcher(config, query) {
    //
}

//创建分发函数
var dispatch1 = dispatcher.bind(null, config1);
var dispatch2 = dispatcher.bind(null, config2);
var dispatch3 = dispatcher.bind(null, config3);

在这里我们不须要改变bind返回的偏函数的this指针。所以bind函数第一个參数传null。

仅仅须要指定一个固定的參数。所以一句话就搞定了。

再说说apply函数。apply和call函数能够方便的实现函数借用。javascript这样的基于原型继承的语言,基础类型的原型为我们提供了很多方便的内建函数,譬如,我要把上面的分发函数写成一个通用的模块。即:把分发行为也抽象出来,由使用者来指定函数行为。createDispatcher仅仅是收集用户參数并调用指定的动作函数:

function createDispatcher(doit, context) {
    var args = Array.prototype.slice.call(arguments, 2);
    return function() {
        doit.apply(context, args.concat(Array.prototype.slice.call(arguments));
    }
}

var obj1 = {name: 'obj1'};
var obj2 = {name: 'obj2'};
var showParams1 = function() {
    console.log(this.name + 'got it: ' + arguments.join('+'));
};

var showParams2 = function() {
    console.log(this.name + 'got it: ' + arguments.join('-'));
};
//obj1 got it: 1+2+3
createDispatcher(showParams1, obj1)(1, 2, 3);
//obj2 got it: 4-5-6
createDispatcher(showParams2, obj2)(4, 5, 6);

apply与call的唯一差别是apply通过数组的形式传參,而call须要把參数列在函数后面,能够觉得apply是javascript语言基于call构造的一个语法糖罢了~

版权声明:本文博主原创文章,博客,未经同意不得转载。

posted @ 2015-10-19 13:28  lcchuguo  阅读(586)  评论(0编辑  收藏  举报