Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/385.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
什么是JavaScript;惯用的;外部解决承诺的方式?_Javascript_Asynchronous_Async Await - Fatal编程技术网

什么是JavaScript;惯用的;外部解决承诺的方式?

什么是JavaScript;惯用的;外部解决承诺的方式?,javascript,asynchronous,async-await,Javascript,Asynchronous,Async Await,在一个项目中,我发现外部可解决承诺的概念(因为没有更好的词)很有用。用例是:某些值在程序中的多个位置都需要,但在一个特定位置异步计算(作为其他工作的一部分)。因此,我们的想法是预先定义一个全局变量,以保证该值: 让变量=可结算承诺() (其中可结算承诺是一个效用函数-见下文) 无论什么地方需要这个值,我们都可以简单地。然后或等待变量(因为它已经被分配了一个承诺) 程序中计算该值的位置将调用variable.solite(x),其中x是计算值 这个方案是可行的,但我想知道是否有一种更标准的方法,而

在一个项目中,我发现外部可解决承诺的概念(因为没有更好的词)很有用。用例是:某些值在程序中的多个位置都需要,但在一个特定位置异步计算(作为其他工作的一部分)。因此,我们的想法是预先定义一个全局变量,以保证该值:

让变量=可结算承诺()

(其中可结算承诺是一个效用函数-见下文)

无论什么地方需要这个值,我们都可以简单地。然后或等待变量(因为它已经被分配了一个承诺)

程序中计算该值的位置将调用variable.solite(x),其中x是计算值

这个方案是可行的,但我想知道是否有一种更标准的方法,而不是下面所示的“可结算承诺”功能。其功能是产生一个可由外部解决的承诺:

function settlablePromise()
{
    let resolver = null;
    let p = new Promise( (resolv,err) => {
        resolver  = resolv;
    });
    p.settle = function(v)
    {
        resolver(v);
    };
    return p;
}
这项计划有效,但我想知道是否有一种更标准的方法

很大程度上,答案是:不要相反,请执行以下操作:

const variable = xyz();
…并使
xyz
成为代码中可以获取值的部分,而不是让该代码调用
变量。稍后结算(x)
。公开结算方法的问题在于,它们可以被任何代码调用,可能不止一次,但只有被调用的第一个会对承诺产生影响。因此,设计有意地使那些人成为创造承诺的代码的私有者。如果没有一些异步操作已经启动,它可以报告任务的完成,那么承诺就没有意义了

如果执行异步工作的代码尚未准备好立即开始工作,您仍然可以让
xyz
返回一个承诺,并让该代码稍后开始该过程。结算方法将保持该代码的私有性,而不是暴露于所有代码中,从而保持封装

这是一个罕见的用例,通常您希望在创建承诺时开始工作。但在这种罕见的情况下,您可以在不公开结算功能的情况下完成此操作

例如:

//在特定于异步工作的模块中
让[承诺,开始]=(()=>{
让我们开始;
持续承诺=新承诺((解决、拒绝)=>{
开始=()=>{
//…实际开始工作,通过调用
//“解决”或“拒绝…”。。。
};
});
回报[承诺,开始];
})();
导出函数xyz(){//作品的公共面
回报承诺;
}
//模块中其他地方的代码通过“启动”启动流程`
您甚至可以直接公开承诺,而不是将其作为函数调用的结果:

//在特定于异步工作的模块中
让[promiseOfNiftyStuff,start]=(()=>{
让我们开始;
持续承诺=新承诺((解决、拒绝)=>{
开始=()=>{
//…实际开始工作,通过调用
//“解决”或“拒绝…”。。。
};
});
回报[承诺,开始];
})();
出口{PROMISEOFFINTYSTUFF};
//模块中其他地方的代码通过“启动”启动流程`
同样,这是一个罕见的用例

非常友好地提供了一个“罕见”用例的很好的例子,在这个用例中,您需要将结算处理程序泄漏到包含的上下文中,并且仍然保持它的良好封装(在本例中是到
fromEvent
):

异步函数*fromEvent(元素,事件){
让resolve=null;
元素。addEventListener(事件,(事件)=>{
解决(事件);
});
while(true){
产生新的承诺(r=>{
解析=r;
})
}
}
异步函数run(){
const button=document.getElementById('test');
用于等待(fromEvent的常量事件(按钮“单击”)){
console.log('clicked');
}
}
run()
单击
这项计划有效,但我想知道是否有一种更标准的方法

很大程度上,答案是:不要相反,请执行以下操作:

const variable = xyz();
…并使
xyz
成为代码中可以获取值的部分,而不是让该代码调用
变量。稍后结算(x)
。公开结算方法的问题在于,它们可以被任何代码调用,可能不止一次,但只有被调用的第一个会对承诺产生影响。因此,设计有意地使那些人成为创造承诺的代码的私有者。如果没有一些异步操作已经启动,它可以报告任务的完成,那么承诺就没有意义了

如果执行异步工作的代码尚未准备好立即开始工作,您仍然可以让
xyz
返回一个承诺,并让该代码稍后开始该过程。结算方法将保持该代码的私有性,而不是暴露于所有代码中,从而保持封装

这是一个罕见的用例,通常您希望在创建承诺时开始工作。但在这种罕见的情况下,您可以在不公开结算功能的情况下完成此操作

例如:

//在特定于异步工作的模块中
让[承诺,开始]=(()=>{
让我们开始;
持续承诺=新承诺((解决、拒绝)=>{
开始=()=>{
//…实际开始工作,通过调用
//“解决”或“拒绝…”。。。
};
});
回报[承诺,开始];
})();
导出函数xyz(){//作品的公共面
回报承诺;
}
//模块中其他地方的代码通过“启动”启动流程`
您甚至可以直接公开承诺,而不是将其作为函数调用的结果:

//在特定于异步工作的模块中
让[允诺]第十五条