详解JavaScript作为命名空间的函数

8.5 作为命名空间的函数

函数作用域,在函数中声明的变量在整个函数体内都是可见的,函数外部是不可见的。

不在任何函数内声明的变量是全局变量,整个JS程序中都是可见的。

JS中无法声明只在一个代码块内可见的变量,基于这个原因,我们常常简单的定义一个函数用作临时的命名空间,在这个命名空间内定义的变量都不会污染到全局命名空间。

比如:假设你写一段JS模块代码,这段代码是共用的,定义了一个存储中间计算结果的变量,问题来了,放到不同程序执行时,无法得知这个变量是否已经创建,若存在这个变量,将会和代码冲突,解决方法当然是将代码放入一个函数内,然后调用这个函数。这样全局变量就变成了函数内的局部变量。

function mymodule(){
    //这个模块所使用的所有变量都是局部变量
    //而不是污染全局命名空间
}
mymodule();

这样还是太麻烦,可以直接定义一个匿名函数,并在单个表达式中调用它:

(function(){
    //模块代码
}());//结束函数并立即调用它

这种定义匿名函数并立即在单个表达式中调用它的写法非常常见,已经成为一种惯用法了。

8.5.1特定场景下返回带补丁的extend()版本


//定义一个拓展函数,用来将第二个以及后续参数复制到第一个参数
//这里我们处理了IE bug:在多数IE版本中,如果o的属性拥有一个不可枚举的同名属性,则
//for/in循环不会枚举对象o的可枚举属性,也就是说将不会正确的处理诸如toString的属性。
//除非我们显式检测它
//将函数的返回值赋值给extend
var extend = (function() {
    //修复之前检查是否存在bug
    for (var p in {
            toString: null
        }) {
        //一个简单版本的extend()函数
        return function extend(o) {
            for (var i = 1; i < arguments.length; i++) {
                var source = arguments[i];
                for (var prop in source) {
                    o[prop] = source[prop];
                }
            }
            return o;
        };
    }
    //返回另一个版本的extend()函数
    return function patched_extend(o) {
        for (var i = 1; i < arguments.length; i++) {
            var source = arguments[i]; //复制所有的可枚举属性
            for (var prop in source) {
                o[prop] = source[prop]; //现在检查特殊属性
                for (var j = 0; j < protoprops.length; j++) {
                    prop = protoprops[j];
                    if (source.hasOwnProperty(prop)) {
                        o[prop] = source[prop];
                    }
                }

            }
        }
        return o;
    };
    //需要检查特殊的属性列表
    var protoprops = ["toString", "valueOf", "constructor", "hasOwnProperty", "isPrototypeOf",
        "propertyIsEnumerable", "toLocaleString"
    ];
}());

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

阿立聊全栈

有作用的,有闲钱的支持一点。

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值