Javascript 调用then函数时如何触发回调?
我发现了一个定制的js promise实现,并试图理解它,但我无法理解如何执行或触发回调,因为promise的定义是立即调用的,但我们只是在实现中推进回调数组Javascript 调用then函数时如何触发回调?,javascript,promise,Javascript,Promise,我发现了一个定制的js promise实现,并试图理解它,但我无法理解如何执行或触发回调,因为promise的定义是立即调用的,但我们只是在实现中推进回调数组 有人能澄清这一点吗首先,这是对承诺的一种特别糟糕的执行,因为它做了各种各样的错事: 它不会在当前执行线程完成后异步解析,这可能会导致不一致的计时问题 它不支持正确链接.then().then()其中.then()返回一个新的承诺,因此第二个.then()仅在解决第一个承诺后调用其处理程序 它不支持正确的链接,.then()回调处理程序可
有人能澄清这一点吗首先,这是对承诺的一种特别糟糕的执行,因为它做了各种各样的错事:
.then().then()
其中.then()
返回一个新的承诺,因此第二个.then()
仅在解决第一个承诺后调用其处理程序.then()
回调处理程序可以返回将插入到链中的承诺.then()
处理程序.then()
或.catch()
处理程序中的同步异常,并将它们转换为被拒绝的承诺.then()
所做的是注册一个回调(保存它),以便在将来某个时候调用它。因此,很自然,它只需向数组中添加一个回调,然后该数组中的回调就可以在将来某个时候执行(比如当承诺兑现时)
在此实现中,definitionFunction()
是承诺的执行者。它是传递给newpromise(fn)
构造函数的回调,应该立即调用它
.then()
回调随后存储在一个数组中
然后,稍后调用执行器中的resolver()
函数时,它将使用this.thenCallbacks.forEach()
迭代该数组,并调用数组中的每个函数
但是,这种实现在很多方面都不能正常工作。如果立即调用resolver()
,那么.thenCallbacks
数组将为空,因为.then()
尚未对承诺进行调用,然后当稍后对已解析的承诺调用.then()
时,它永远不会调用回调
正如我在评论中所说,我不想再花时间讨论这样一个有缺陷的承诺是如何实现的。我试图回答您的直接问题,并引导您实现更好、更准确、更完整的承诺,您可以继续研究。这一个有各种各样的问题,所以,在我看来,不值得花更多的时间去理解它是如何工作的
您还可以花一些时间阅读,阅读或理解起来并不复杂。我不理解您的要求,但此promise实现不符合规范,因为它在解决promise时立即调用
。然后()
处理程序,而不是在事件循环的下一个刻度上。它也不处理承诺链接(当.then()
处理程序返回另一个承诺时)。是的,我知道根据规范,这不是完美的实现,但我想了解我们只是将回调推到thenarray中,但它们是如何及时执行或触发的,您仍然可以在此实现中链接then。请检查playcode链接All。然后()
应该做的是注册稍后可以调用的回调(当承诺被解决或拒绝时)。还是不明白你在问什么。在这种情况下,“注册”意味着将它们放入一个数组中以保存它们以供以后使用。此实现还存在许多其他问题,因为它也没有调用.then()
处理程序,因为它是在承诺已经解决之后添加的。我不是说链接.then().then()
。我说的是从.then()
处理程序返回一个新的承诺,该处理程序应该将该新承诺插入到链中,但这不起作用。基本上,这是大约20%的实现。
function myPromise(definitionFunction){
this.thenCallbacks = [];
this.status = 'pending';
this.value = undefined;
definitionFunction(resolver.bind(this),rejector.bind(this));
function resolver(value)
{
this.status = 'resolved';
this.value = value;
this.thenCallbacks.forEach(function(func){
console.log(func);
this.value = func(this.value);
},this);
}
function rejector(value)
{
}
}
myPromise.prototype.then = function(successCallback,errorCallback){
this.thenCallbacks.push(successCallback);
return this;
}
var test = new myPromise(function(resolve,reject){
var xhttp = new XMLHttpRequest();
var url = "https://jsonmock.hackerrank.com/api/stocks/search?page="+1;
xhttp.open("GET",url , true);
xhttp.onload = function() {
if (this.readyState == 4 && this.status == 200) {
resolve(this.responseText);
}
else
{
reject({
status: this.status,
statusText: xhttp.statusText
})
}
};
xhttp.onerror = function() {
reject({
status: this.status,
statusText: xhr.statusText
});
}
xhttp.send();
});
test.then((response)=>'kiran').then((resp)=>{return{name:'kiran'}}).then((resp)=>console.log(resp));