28

让我们创建一个简单的 Deferred 对象:

defer = $.Deferred( function ( defer ) {
    setTimeout( defer.resolve, 3000 );
});

上述 Deferred 对象将处于“pending”状态 3 秒,然后切换到“resolved”状态(此时将调用与其绑定的所有回调)。

让我们也检索该 Deferred 对象的承诺:

promise = defer.promise();

现在,要添加在 Deferred 对象被解析后将被调用的回调,我们可以使用.done()or .then()。但是,我们可以在 Deferred 对象本身或它自己的 Promise 对象上调用此方法

defer.then( handler );

或者

promise.then( handler );

在这两种情况下,handler都会调用该函数(在这种情况下是 3 秒后)。

如果我们使用$.when,我们可以再次传递 Deferred 对象本身或其承诺对象:

$.when( defer ).then( handler );

或者

$.when( promise ).then( handler );

同样,上述两行代码之间没有区别。

现场演示:http: //jsfiddle.net/G6Ad6/

所以,我的问题是,既然我们可以在 Deferred 对象本身上调用.then(),.done()等,并且因为我们可以将该 Deferred 对象传递给$.when(),那么.promise()检索 Promise 对象的意义何在?承诺对象的目的是什么?为什么在功能上有这种冗余?

4

3 回答 3

25

它创建了延迟值的“密封”副本,没有.resolve()and.reject()方法。从文档中

deferred.promise()方法允许异步函数防止其他代码干扰其内部请求的进度或状态。

当要修改的值没有意义时使用它。例如,当 jQuery 发出 AJAX 请求时,它会返回一个 Promise 对象。在内部,它.resolve()是原始Deferred对象的值,用户通过承诺观察到。

于 2011-11-10T00:16:54.483 回答
2

当使用 Deferred 对象的“承诺”时,观察者(例如等待解析的对象)不能直接访问 Deferred 对象本身,因此他们不能调用例如该 Deferred 的方法“Resolve”。这是一种保护原始 Deferred 的方式。

于 2013-12-18T09:33:48.553 回答
0

使用 Deferred,您可以控制其状态set

当涉及到 Promise 时,您可以读取状态并可能附加回调。get

于 2015-11-12T09:18:52.510 回答