停止等待 setTimeOut 函数
stop await setTimeOut function
我有一个名为 delay() 的 Typescript 函数,它在 async/await 模式下被调用。
play(){
(async () => {
await this.delay(90000);
this.player.play();
})();
}
delay(ms: number) {
return new Promise(resolve => setTimeout(resolve, ms));
}
有没有办法在"play"函数再次调用时"kill/interrupt"完成90秒之前的setTimeout并重新开始计数?
setTimeout
returns 一个值。将该值保存在某处,然后当您想要 "kill/interrupt" 它时,对其调用 clearTimeout
。
因为你的取消函数 returns 是一个 promise,而 ES6 不允许你取消一个 promise。承诺 returns 成功或失败值。
要取消承诺,请使用
RxJS observables 或像 bluebird 这样的第三方库
你可能想要这样的东西
const delay = (ms: number) => {
let id;
const promise = new Promise(resolve => {
id = setTimeout(resolve, ms);
});
return {
id, promise
};
}
const play = () => {
const { id, promise } = delay(1000);
promise.then(() => console.log("Promise called"));
// Or call this to cancel
clearTimeout(id);
};
但我会用另一种方式实现它:
const Timer = (ms: number) => {
let id: number;
const start = () => new Promise(resolve => {
if (id === -1) {
throw new Error('Timer already aborted');
}
id = setTimeout(resolve, ms);
});
const abort = () => {
if (id !== -1 || id === undefined) {
clearTimeout(id);
id = -1;
}
}
return {
start, abort
}
};
const timer = Timer(1000);
timer.start().then(() => console.log("done after 1000ms"));
timer.abort(); // this would abort the operation
// Calling timer.abort() before timer.start() would throw an error as well.
看看这是否有帮助。
想法是我们创建一个 settimeout 参考变量,我们可以使用它来执行 clearTimeout,以停止先前的 settimeout 执行。
play = (()=>{let timeoutRef; return((number)=>{if(timeoutRef){clearTimeout(timeoutRef)};timeoutRef = setTimeout(()=>console.log("hello",number),number)})})()
注意代码格式,我使用 jsconsole 输入我的代码。:)
看看 "debounced" 函数。
import { debounce } from “lodash”;
class Player {
constructor() {
this.delayedPlay = debounce(this.play.bind(this), 9000);
}
play() {
/* do stuff here */
}
}
如果您在第一次呼叫前不到 90 秒内再次呼叫 debouncePlay
,第一次呼叫将被取消,新的计时器将开始计时。
Here is a more detailed explanation of the debounce function.
您可以阅读 关于 Promise 取消的内容。
我创建了一个 class 可以帮助您解决问题
我的 class 正在利用 bluebird 库
的优点
class Delayer {
constructor() {
this.Promise = require('bluebird');
this.Promise.config({
cancellation: true
})
this.promise = null;
}
delay(ms) {
if(this.promise) {
this.promise.cancel();
}
this.promise = new this.Promise(resolve => setTimeout(resolve, ms));
return this.promise;
}
}
您的代码用法
// you need to run `npm install bluebird --save`
const delayer = new Delayer(); // create a new instance of delayer to work with
play(){
(async () => {
await delayer.delay(90000);
this.player.play();
})();
}
我有一个名为 delay() 的 Typescript 函数,它在 async/await 模式下被调用。
play(){
(async () => {
await this.delay(90000);
this.player.play();
})();
}
delay(ms: number) {
return new Promise(resolve => setTimeout(resolve, ms));
}
有没有办法在"play"函数再次调用时"kill/interrupt"完成90秒之前的setTimeout并重新开始计数?
setTimeout
returns 一个值。将该值保存在某处,然后当您想要 "kill/interrupt" 它时,对其调用 clearTimeout
。
因为你的取消函数 returns 是一个 promise,而 ES6 不允许你取消一个 promise。承诺 returns 成功或失败值。
要取消承诺,请使用
RxJS observables 或像 bluebird 这样的第三方库
你可能想要这样的东西
const delay = (ms: number) => {
let id;
const promise = new Promise(resolve => {
id = setTimeout(resolve, ms);
});
return {
id, promise
};
}
const play = () => {
const { id, promise } = delay(1000);
promise.then(() => console.log("Promise called"));
// Or call this to cancel
clearTimeout(id);
};
但我会用另一种方式实现它:
const Timer = (ms: number) => {
let id: number;
const start = () => new Promise(resolve => {
if (id === -1) {
throw new Error('Timer already aborted');
}
id = setTimeout(resolve, ms);
});
const abort = () => {
if (id !== -1 || id === undefined) {
clearTimeout(id);
id = -1;
}
}
return {
start, abort
}
};
const timer = Timer(1000);
timer.start().then(() => console.log("done after 1000ms"));
timer.abort(); // this would abort the operation
// Calling timer.abort() before timer.start() would throw an error as well.
看看这是否有帮助。 想法是我们创建一个 settimeout 参考变量,我们可以使用它来执行 clearTimeout,以停止先前的 settimeout 执行。
play = (()=>{let timeoutRef; return((number)=>{if(timeoutRef){clearTimeout(timeoutRef)};timeoutRef = setTimeout(()=>console.log("hello",number),number)})})()
注意代码格式,我使用 jsconsole 输入我的代码。:)
看看 "debounced" 函数。
import { debounce } from “lodash”;
class Player {
constructor() {
this.delayedPlay = debounce(this.play.bind(this), 9000);
}
play() {
/* do stuff here */
}
}
如果您在第一次呼叫前不到 90 秒内再次呼叫 debouncePlay
,第一次呼叫将被取消,新的计时器将开始计时。
Here is a more detailed explanation of the debounce function.
您可以阅读
我创建了一个 class 可以帮助您解决问题
我的 class 正在利用 bluebird 库
class Delayer {
constructor() {
this.Promise = require('bluebird');
this.Promise.config({
cancellation: true
})
this.promise = null;
}
delay(ms) {
if(this.promise) {
this.promise.cancel();
}
this.promise = new this.Promise(resolve => setTimeout(resolve, ms));
return this.promise;
}
}
您的代码用法
// you need to run `npm install bluebird --save`
const delayer = new Delayer(); // create a new instance of delayer to work with
play(){
(async () => {
await delayer.delay(90000);
this.player.play();
})();
}