《Javascript高级程序设计》读书笔记之闭包

闭包

function createComparisonFunction(propertyName) {
    return function (object1, object2) {
        var value1 = object1[propertyName];
        var value2 = object2[propertyName];

        if (value1 < value2) {
            return -1;
        } else if (value1 > value2) {
            return 1;
        } else {
            return 0;
        }
    };
}
//创建函数
var compare = createComparisonFunction("name");
//调用函数
var result = compare({ name: "Jim" }, { name: "Jack" });
//解除对匿名函数的引用,以便释放内存
compare = null;
View Code

匿名函数从createComparisonFunction()中被返回后,它的作用域链被初始化为包含createComparisonFunction()函数的活动对象和全局变量对象。

这样,匿名函数可以访问在createComparisonFunction()中定义的所有变量,同时,createComparisonFunction()函数执行完毕后,其活动对象也不会被销毁,因为匿名对象的作用域链仍然引用这个活动对象。

直到匿名函数呗销毁后,createComparisonFunction()函数的活动对象才会被销毁

闭包与变量

下面代码片段中,片段1中,每个函数的作用域中都保存着createFunctions()函数的活动对象,所以他们都应用的是同一个变量i。createFunctions()函数执行完后,i为5,所以每个匿名函数内部i的值都是5

片段2中,在返回的匿名函数外部,再创建一个匿名函数,并将立即执行该匿名函数的结果赋给数组。函数参数按值传递,变量i的当前值赋值给num,匿名函数内部,创建了访问该num变量的闭包。

//代码片段1
function createFunctions() {
    var result = new Array();
    for (var i = 0; i < 5; i++) {
        result[i] = function () {
            alert(i);
        }
    }
    return result;
}

var funcs = createFunctions();
//Array.forEach()
funcs.forEach(function (item) { item(); }); //5,5,5,5,5


//代码片段2
function createFunctions() {
    var result = new Array();
    for (var i = 0; i < 5; i++) {
        result[i] = function (num) {
            return function () {
                alert(num);
            }
        } (i);
    }
    return result;
}

var funcs = createFunctions();
//Array.forEach()
funcs.forEach(function (item) { item(); }); //0,1,2,3,4
View Code

闭包中的this

var name = "The Window";
var object = {
    name: "My Object",
    getNameFunc: function () {
        return function () {
            return this.name;
        }
    }
};

alert(object.getNameFunc()()); //"The Window"
View Code

object.getNameFunc()返回一个匿名函数,在全局环境调用该函数,this指向的全局对象

解决这一问题,可以将匿名函数外部作用域中this对象保存在闭包能够访问到的变量中

var name = "The Window";
var object = {
    name: "My Object",
    getNameFunc: function () {
        var that = this;
        return function () {
            return that.name;
        }
    }
};

alert(object.getNameFunc()()); //"My Object"
View Code

 

posted @ 2014-10-18 23:05  GongQi  阅读(1120)  评论(2编辑  收藏  举报