我的应用程序中已经使用ECMAScript 6和ECMAScript 7功能(感谢Babel) - 包括移动和网络。
第一步显然是ECMAScript 6级别。我学到了许多异步模式,承诺(非常有前途),生成器(不确定为什么是*符号)等。 其中,承诺非常适合我的目的。我一直在我的应用程序中使用它们。
这是我如何实现基本承诺的示例/伪代码 -
var myPromise = new Promise(
function (resolve,reject) {
var x = MyDataStore(myObj);
resolve(x);
});
myPromise.then(
function (x) {
init(x);
});
随着时间的推移,我遇到了ECMAScript 7功能,其中一个是ASYNC
和AWAIT
关键字/功能。这些结合起来有很大的奇迹。我已经开始用async & await
替换我的一些承诺。它们似乎为编程风格增添了很多价值。
同样,这里是我的异步,等待函数的伪代码 -
async function myAsyncFunction (myObj) {
var x = new MyDataStore(myObj);
return await x.init();
}
var returnVal = await myAsyncFunction(obj);
保持语法错误(如果有的话),两者都做同样的事情就是我的感受。我几乎能够用异步替换我的大部分承诺,等待着。
为什么在承诺做类似的工作时需要异步,等待?
async,等待解决更大的问题吗?或者它只是回调地狱的另一种解决方案?
正如我之前所说,我能够使用promises和async,等待解决同样的问题。是否存在异步等待解决的具体内容?
附加说明:
我一直在我的React项目和Node.js模块中广泛使用异步,等待和承诺。 React特别是早期的鸟类,并采用了很多ECMAScript 6和ECMAScript 7的功能。
答案 0 :(得分:56)
当Promises做类似的工作时,为什么需要async,等待? async,等待解决更大的问题吗?
async/await
简单地为您提供异步代码的同步感觉。这是一种非常优雅的语法糖形式。
对于简单的查询和数据操作,Promise可以很简单,但是如果遇到复杂的数据操作和涉及的内容的场景,如果代码只是看起来,那么更容易理解发生了什么虽然它是同步的(换句话说,语法本身就是async/await
可以解决的“偶然复杂性”的形式。
如果您有兴趣知道,可以使用像co
这样的库(与生成器一起)来提供相同的感觉。已经开发出类似这样的东西来解决async/await
最终解决的问题(原生)。
答案 1 :(得分:27)
Async / Await在更复杂的场景中提供了更好的语法。特别是,任何涉及循环或某些其他结构的内容,例如try
/ catch
。
例如:
while (!value) {
const intermediate = await operation1();
value = await operation2(intermediate);
}
这个例子使用Promise会更加复杂。
答案 2 :(得分:7)
我的问题是,为什么Promises确实需要异步等待 类似的工作?异步等待解决更大的问题吗?还是只是一个 回调地狱的不同解决方案?就像我之前说的,我能够 使用Promises和Async,Await解决相同的问题。在那儿 异步等待解决了什么具体问题?
首先要了解的是async
/ await
语法仅仅是语法糖,旨在增强承诺。实际上,async
函数的返回值是一个承诺。 async
/ await
语法使我们能够以同步方式编写异步代码。这是一个示例:
承诺链接:
function logFetch(url) {
return fetch(url)
.then(response => response.text())
.then(text => {
console.log(text);
}).catch(err => {
console.error('fetch failed', err);
});
}
Async
功能:
async function logFetch(url) {
try {
const response = await fetch(url);
console.log(await response.text());
}
catch (err) {
console.log('fetch failed', err);
}
}
在上面的示例中,await
等待诺言(fetch(url)
)被解决或被拒绝。如果承诺已解决,则将值存储在response
变量中,如果承诺被拒绝,则会抛出错误,从而进入catch
块。
我们已经看到,使用async
/ await
可能比诺言链更具可读性。当我们使用的承诺数量增加时,尤其如此。 Promise链接和async
/ await
都解决了回调地狱的问题,您选择哪种方法取决于个人喜好。
答案 3 :(得分:6)
Async / await可以帮助您在需要复杂控制流的情况下使代码更清晰,更易读。它还可以生成更多适合调试的代码。并且只需try/catch
即可处理同步和异步错误。
我最近写了这篇文章,展示了在代码示例https://hackernoon.com/6-reasons-why-javascripts-async-await-blows-promises-away-tutorial-c7ec10518dd9
的一些常见用例中async / await优于promises的优点答案 4 :(得分:6)
与利弊完全比较。
普通JavaScript
- 不需要任何其他库或技术
- 表现最佳性能
- 提供与第三方库的最佳兼容性
- 允许创建临时和更高级的算法
- 可能需要额外的代码和相对复杂的算法
异步(库)
- 简化最常见的控制流程模式
- 仍然是基于回调的解决方案
- 表现良好
- 介绍外部依赖
- 可能仍然不适合高级流程
<强>承诺强>
- 大大简化最常见的控制流程模式
- 强大的错误处理
- ES2015规范的一部分
- 保证延迟调用onFulfilled和onRejected
- 需要promisify基于回调的API
- 推出小型演出
<强>发电机强>
- 使非阻塞API看起来像阻塞的
- 简化错误处理
- ES2015规范的一部分
- 需要补充控制流程库
- 仍需要回调或承诺来实施非连续流动
- 需要thunkify或promisify基于非生成器的API
异步等待
- 使非阻塞API看起来像阻止
- 清晰直观的语法
- 今天需要使用Babel或其他转发器以及一些配置
答案 5 :(得分:2)
承诺
Promise对象表示异步操作的可能完成(或失败)及其结果值。它是在创建时未必知道的值的代理,它表示异步操作的未来结果。
在执行下一步之前,调用代码可以等待直到实现了诺言。为此,promise具有名为then
的方法,该方法接受一个函数,该函数将在实现诺言时被调用。
异步/等待
调用async
函数时,它将返回一个Promise
。当async
函数返回一个值时,将使用返回的值解析Promise
。当async
函数抛出异常或某个值时,Promise将被抛出的值拒绝。
异步函数可以包含await表达式,该表达式会暂停异步函数的执行并等待所传递的Promise的分辨率,然后恢复异步函数的执行并返回解析的值
异步/等待承诺的优点