2012-06-17 39 views
9

保持在代码中看到这种模式,但在google或SO中找不到任何引用,奇怪。有人可以指向我参考this.async()函数吗?JavaScript中的this.async()做什么

var done = this.async(); 
    // ... 
    $.get(path, function(contents) { // or some other function with callback 
    // ... 
    done(JST[path] = tmpl); 
    }) 
+7

这不是内置功能。它必须由一些图书馆/框架提供。 – user123444555621

回答

1

这是一种解决this转义内部问题的方法。没有这个额外的参考代码将看起来像这样:

$.get(path, function(contents) { // or some other function with callback 
    //Wrong! `this` might no longer point to your object 
    this.done(JST[path] = tmpl); 
}) 

不幸的是! this里面的响应回调与其外部的this不一样。实际上,它可以是任何东西,具体取决于$.get(调用回调函数)决定它。大部分的人使用相同的目的命名that额外的参考:

var that = this; 
// ... 
$.get(path, function(contents) { // or some other function with callback 
    // ... 
    that.async(JST[path] = tmpl); 
}) 

这种模式也似乎合理性和可读性。

哦,如果你是好奇这句法:

done(JST[path] = tmpl) 

这是作为一个表达式赋值。分配的值是右手侧,所以该代码相当于:

JST[path] = tmpl; 
done(tmpl); 
+4

-1:这不会回答有关'this.async()'的问题,而是会谈论甚至在问题中不会发生的问题。我很困惑,为什么@托尼接受了这个答案。 – fluffy

16

var done = this.async()done(blah)是一个聪明的特技返回从一个同步函数内异步呼叫(例如$.get)取一个值。

让我们看一个例子:

var getText = function() { 
    return "hello"; 
}; 
var text = getText(); 

这是一个非常简单的函数调用所以在这里没有任何的难题。但是,如果您需要在getText()函数中异步获取文本呢?

var getText = function() { 
    return $.get('<some-url>', function(text) { 
    return text; 
    }); // ?????? 
}; 

致电getText()不会返回您想要获得的文本。它返回jQuery的承诺对象。

那么我们怎样才能让getText()返回文字从$.get()得到调用?

var getText = function() { 
    var done = this.async(); 
    $.get('<some-url>', function(text) { 
    done(text); 
    }); 
}; 
var text = getText(); // you get the expected text 

魔法吧?

我不知道this.async()的内部工作电话呢。我不知道是否有一个库提供该功能,但您可以看到Backbone.LayoutManager使用这个技巧https://github.com/tbranyen/backbone.layoutmanager/blob/master/backbone.layoutmanager.js(搜索this.async)。

此外,Tim Branyen(骨干布局管理者的作者)在他的视频教程(http://vimeo.com/32765088大约14:00 - 15:00)中对此进行了简要介绍。蒂姆说,在视频中,本·阿尔曼提出了这个诀窍。看看这个以及https://github.com/cowboy/javascript-sync-async-foreach

我认为这是一个非常巧妙的技巧混合异步和同步功能。

干杯,

+0

我在Yeoman'创建生成器'教程(http://yeoman.io/authoring/user-interactions.html)中遇到了这个问题。 – devboell