【问题标题】:How to call clearTimeout and still run the setTimeout's function?如何调用 clearTimeout 并仍然运行 setTimeout 的功能?
【发布时间】:2020-11-13 06:46:34
【问题描述】:

这是我的代码:

let delayTimeout = null;
const delayExecution = mls => {
    console.log('Delaying for', mls);
    return new Promise(resolve => {
        delayTimeout = setTimeout(() => resolve('ok'), mls);
    })
}

const main = async () => {
    axios.post('URL', {data})
             .then(response => {
                 if(response passes some condition){
                     clearTimeout(delayTimeout);
                 }
             })

   const res = await delayExecution(30000)
   console.log("DONE!")
}

main();

在 axios 调用之后,我可能想通过清除其中的超时来终止 delayExecution。如何在我的 delayExecution 函数中清除超时但仍解决 Promise?

本质上,我试图在它的时间之前完成delayExecution,但仍然解决其中的承诺。

【问题讨论】:

  • 我真的不明白你在做什么。如果您不想清除超时 - 因为您希望函数在 10 秒后仍然执行 - 那么就不要调用 clearTimeout
  • 取决于 /* Seome logic here */ 我可能希望函数在 10 秒之前执行。
  • 所以你想有条件地改变超时的持续时间?那为什么不根据你需要的任何逻辑设置一个变量,比如duration,然后在最后做setTimeout(doneFunc, duration)? (但我可能仍然不了解您的要求。)
  • 不是我想有条件地改变超时的持续时间,而是在某些情况下,我希望setTimeout函数早点完成,这种情况下我仍然想要doneFunc函数运行。
  • 您的 setTimeOut 函数精确地用于在延迟后执行您的 doneFunc 函数。如果您希望它在之前运行,请不要使用 setTimeOut

标签: javascript


【解决方案1】:

根据您的编辑,我将留下另一个回复。请注意,我还没有测试过,我的注意力目前集中在我正在编写的代码上,呵呵

let delayTimeout = null;
let resolveHandler = null;
const delayExecution = mls => {
    console.log('Delaying for', mls);
    return new Promise(resolve => {
        resolveHandler = resolve;
        delayTimeout = setTimeout(() => resolve('ok'), mls);
    })
}

const main = async () => {
    axios.post('URL', {data})
             .then(response => {
                 if(response passes some condition){
                     resolveHandler('ok');
                     clearTimeout(delayTimeout);
                 }
             })

   const res = await delayExecution(30000)
   console.log("DONE!")
}

main();

这个想法只是将解析函数分配给另一个辅助变量,然后您可以在其他地方使用它:)

【讨论】:

  • 是的先生!奇迹般有效。谢谢。
  • 很高兴为您提供帮助,老兄 :) 加我到linkedin,我们可以保持联系
【解决方案2】:

doneFunc 里面应该有 clearTimeout,所以函数完成后超时就会被清除。

另外,对于第一个 setTimeout 参数,您可以只传递函数的名称。

实际上对于超时,您不需要 clearTimeout,因为与继续运行的间隔相比,它只会运行一次。

const doneFunc = () => {console.log('Finished job');clearTimeout(f);}

const f = setTimeout(doneFunc, 100);

【讨论】:

  • 我知道它只会运行一次,但在某些情况下,我希望该运行早点完成,在这种情况下,我希望 doneFunc 仍然触发。
【解决方案3】:

如果您想独立于超时运行该函数,只需在其外部声明该函数,然后在需要时调用它。你已经完成了大部分代码

const doneFunc = () => console.log('Finished job');

const f = setTimeout(() => doneFunc(), 10000);

/* Seome logic here */

if (condition to run before timeout) {
  clearTimeout(f);
 doneFunc();

}

/* end of logic */

【讨论】:

  • 这看起来像这里的解决方案。可能会删除最终的 clearTimeout。
  • 这是一个很好的观点。问题当然是 doneFunc 不是那么容易直接运行。为了简洁起见,我提供的代码非常简单。在生产中,我的 setTimeout 函数实际上触发了对 Promise 的解析,我不确定如何直接调用它。我应该更好地解释我的要求。所以我要稍微调整一下这个问题。
【解决方案4】:

我想象过:

const runOnDelay = function( fct, delay )
        {
        let obj    = {}
          , isDone = false
          , refTim = setTimeout(()=>
              {
              isDone = true
              fct()
              }, delay)
          ;
        obj.stop = () =>
          { 
          clearTimeout(refTim)
          if (!isDone)
            fct()
          isDone = true
          }
        return obj
        }

用法:

const doneFunc = () => console.log('Finished job')

let myBoy = runOnDelay(doneFunc, 1000)

 //...

myBoy.stop()

【讨论】:

  • 这实际上是一段非常简洁的代码。围绕它重写我当前的逻辑对我来说工作量太大,但我无疑会在我的应用程序的其他地方使用它。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-12-10
  • 2021-09-23
  • 1970-01-01
  • 2011-03-02
相关资源
最近更新 更多