如何在 javascript ES6 类 中链接异步方法
How to chain async methods in javascript ES6 classes
我想从 class 链接方法。我有同步方法的问题,但我不知道如何使用异步方法。
例如,这个 class:
class Example {
constructor() {
this.val = 0
}
async () {
setTimeout(() => {
this.val += 1
return this
}, 5000)
}
sync () {
this.val += 1
return this
}
check () {
console.log('checker', this.val)
return this
}
}
这个有效:
new Example().sync().check()
> 1
但这行不通:
new Example().async().check()
> TypeError: Cannot read property 'check' of undefined
P.S。我想要链接,而不是地狱回调。
如果您只想 new Example().async().check()
工作,那么您需要做的就是 return this
在调用 setTimeout 之后。例如:
async () {
setTimeout(() => {
this.val += 1
}, 5000)
return this
}
超时中的 return this
不是必需的,因为它会自行执行。那时基本上 运行 是独立的。
真的,如果您希望整个事情 运行 完全异步,并且您能够控制某些事情何时发生的流程,您需要使用 promises 来实现它。
如果您正在使用 async
函数和方法,那么您就是在使用 promises(我想您知道它们,如果不知道,请在继续阅读之前了解它们)。
如果考虑等待,则不应在异步函数内部使用 setTimeout
。相反,为超时创建一个承诺,最好使用这样的辅助函数:
function timeout(ms) {
return new Promise(resolve => {
setTimeout(resolve, ms)
});
}
现在您可以按照自己的意愿编写方法:
class Example {
…
async async () {
await timeout(5000);
this.val += 1;
return this;
}
…
}
当然,作为一个 async
函数,它不是 return 实例本身,而是对实例的承诺。如果你要链接,你将不得不在另一个异步函数中调用它,你可以在其中 await
承诺:
(async function() {
(await (new Example().async())).check();
}());
我想你想在超时结束后调用 check()
。问题是分叉了,你不能立即得到 return.
可用的东西
您可以传入 check()
作为回调:
class Example {
constructor() {
this.val = 0
}
async (callback) {
setTimeout(() => {
this.val += 1
callback()
}, 5000)
}
sync () {
this.val += 1
return this
}
check () {
console.log('checker', this.val)
return this
}
}
// execution
var ex = new Example();
ex.async(ex.check)
...或承诺
class Example {
constructor() {
this.val = 0
}
async (callback) {
var deferred = Q.defer()
setTimeout(() => {
this.val += 1
deferred.resolve();
}, 5000)
return deferred.promise;
}
sync () {
this.val += 1
return this
}
check () {
console.log('checker', this.val)
return this
}
}
// execution
var ex = new Example()
ex.async().then(() => ex.check())
...或者您可以使用 ES6 生成器
你要找的问题Promises. You'll need to likely install a polyfill, like Bluebird or q将得到最优雅的解决。
我会将您的异步方法更改为:
async() {
return new Promise((resolve, reject)=>{
setTimeout(()=>{
this.val += 1;
resolve(this);
}, 5000);
});
}
以及您的调用代码:
new Example().async().then((instance)=>instance.check());
不幸的是,在确定 ES7 异步函数之前,如果没有某种形式的回调,将不会有一种优雅的方式来做到这一点。
我想从 class 链接方法。我有同步方法的问题,但我不知道如何使用异步方法。
例如,这个 class:
class Example {
constructor() {
this.val = 0
}
async () {
setTimeout(() => {
this.val += 1
return this
}, 5000)
}
sync () {
this.val += 1
return this
}
check () {
console.log('checker', this.val)
return this
}
}
这个有效:
new Example().sync().check()
> 1
但这行不通:
new Example().async().check()
> TypeError: Cannot read property 'check' of undefined
P.S。我想要链接,而不是地狱回调。
如果您只想 new Example().async().check()
工作,那么您需要做的就是 return this
在调用 setTimeout 之后。例如:
async () {
setTimeout(() => {
this.val += 1
}, 5000)
return this
}
超时中的 return this
不是必需的,因为它会自行执行。那时基本上 运行 是独立的。
真的,如果您希望整个事情 运行 完全异步,并且您能够控制某些事情何时发生的流程,您需要使用 promises 来实现它。
如果您正在使用 async
函数和方法,那么您就是在使用 promises(我想您知道它们,如果不知道,请在继续阅读之前了解它们)。
如果考虑等待,则不应在异步函数内部使用 setTimeout
。相反,为超时创建一个承诺,最好使用这样的辅助函数:
function timeout(ms) {
return new Promise(resolve => {
setTimeout(resolve, ms)
});
}
现在您可以按照自己的意愿编写方法:
class Example {
…
async async () {
await timeout(5000);
this.val += 1;
return this;
}
…
}
当然,作为一个 async
函数,它不是 return 实例本身,而是对实例的承诺。如果你要链接,你将不得不在另一个异步函数中调用它,你可以在其中 await
承诺:
(async function() {
(await (new Example().async())).check();
}());
我想你想在超时结束后调用 check()
。问题是分叉了,你不能立即得到 return.
您可以传入 check()
作为回调:
class Example {
constructor() {
this.val = 0
}
async (callback) {
setTimeout(() => {
this.val += 1
callback()
}, 5000)
}
sync () {
this.val += 1
return this
}
check () {
console.log('checker', this.val)
return this
}
}
// execution
var ex = new Example();
ex.async(ex.check)
...或承诺
class Example {
constructor() {
this.val = 0
}
async (callback) {
var deferred = Q.defer()
setTimeout(() => {
this.val += 1
deferred.resolve();
}, 5000)
return deferred.promise;
}
sync () {
this.val += 1
return this
}
check () {
console.log('checker', this.val)
return this
}
}
// execution
var ex = new Example()
ex.async().then(() => ex.check())
...或者您可以使用 ES6 生成器
你要找的问题Promises. You'll need to likely install a polyfill, like Bluebird or q将得到最优雅的解决。
我会将您的异步方法更改为:
async() {
return new Promise((resolve, reject)=>{
setTimeout(()=>{
this.val += 1;
resolve(this);
}, 5000);
});
}
以及您的调用代码:
new Example().async().then((instance)=>instance.check());
不幸的是,在确定 ES7 异步函数之前,如果没有某种形式的回调,将不会有一种优雅的方式来做到这一点。