javascript - 看《js设计模式》时,发现个问题...
伊谢尔伦
伊谢尔伦 2017-04-11 13:25:13
[JavaScript讨论组]

我看这里的时候 感觉有个很奇怪的地方:

var getSingle = function( fn ){
    var result;
    return function(){
        return result || ( result = fn .apply(this, arguments ) );
    }
};

在调用 getSingle的时候,每次调用 都会重新声明一个 var result 变量啊, 所以每次 result 都是个新的 空 呀,那后面的判断 就没意义了!!!是不是漏了个立即执行(function(){})() 来包裹一下呀?

伊谢尔伦
伊谢尔伦

小伙看你根骨奇佳,潜力无限,来学PHP伐。

全部回复(4)
天蓬老师

嗯 这书我也看过 《JavaScript设计模式与开发实践》,单例模式那块儿。

其实这是一个闭包的问题

你看这一行

var createSingleLoginLayer = getSingle(createLoginLayer)

返回的这个 createSingleLoginLayer 函数始终引用了 result 变量。

因此假设 无论是 createSingleLoginLayer(args1) 还是 createSingleLoginLayer(args2) 其实result 变量从来都是那个一开始那个 result .每次 result 不是空的。

说到底,这就是个闭包的问题。

迷茫

@499311496 说的是对的。
这个getSingle是把创建单例的方法也抽象出来,每次调用getSingle,result的确会被再创建一次。但是第二次创建的跟第一次是没有关系的。比如:

var createSingleLoginLayer = getSingle(createLoginLayer)

上面result被创建了一次,但是我是用于创建登录窗口的。我接着再使用:

var createSingleLogoutLayer = getSingle(createLogoutLayer)

result又被创建了一次,但是这个时候两个result也都是存在的,并且是不一样的。我现在即可以使用createSingleLoginLayer又可以使用reateSingleLogoutLayer。

伊谢尔伦

题主说的没有问题,每次调用getSingle的时候都会重新声明一个result,但是书上没有写错,getSingle的作用并不是获得单例,而是获得生产单例的函数,createSingleIframe()函数才是获得单例;每次运行createSingleIframe()函数其中的result不会被重新声明,因为createSingleIframe()函数每次执行的是返回的函数。

var createFrame = (function(){
    var iframe;
    return function() {
        if(!iframe) {
            // 创建iframe
        }
        return iframe
    }
})()

去掉自执行函数

var test= function(){
    var iframe;
    return function() {
        if(!iframe) {
            // 创建iframe
        }
        return iframe
    }
} // test每次执行iframe都不一样但是它一次执行的值,肯定是一样的,所以如下:
createFrame = test() 
// createFrame()每次执行运行的是test的返回值(函数),它获取的iframe应该是一样的,
// 这个test就和题目中的getSingle作用类似

继续改变使用getSingle

var getSingle = function( fn ){
    var result;
    return function(){
    // 这个返回函数才是每次执行的函数,result的值在第一次确定之后就不会改变了
        return result || ( result = fn .apply(this, arguments ) ); 
        // 这里又重复了上面提到的概念,result = fn .apply(this, arguments),
        // fn .apply(this, arguments)每次执行都是不一样的,
        // 但是result()其实获取的某一次执行的值,这个是一样,所以每次获取的其实是同一个值。
    }
};

说了这么多其实这个转变最主要的是理解:

var test1 = function (){
    return test
}
test2 = test1() // test1是返回test,test2是执行test函数
PHPz

每次调用getSingle都会创建result,这个result对于返回的函数来讲是唯一存在的,
var fn = getSingle(otherFn)
这个fn始终可以访问这个唯一的result,

var fn2 = getSingle(otherFn2)
这个fn2也包装了一个result

闭包创建了一个返回函数的私有属性罢了

热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新 English
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号