2715. 执行可取消的延迟函数
2715. 执行可取消的延迟函数
题目
Given a function fn, an array of arguments args, and a timeout t in milliseconds, return a cancel function cancelFn.
After a delay of cancelTimeMs, the returned cancel function cancelFn will be invoked.
setTimeout(cancelFn, cancelTimeMs)
Initially, the execution of the function fn should be delayed by t milliseconds.
If, before the delay of t milliseconds, the function cancelFn is invoked, it should cancel the delayed execution of fn. Otherwise, if cancelFn is not invoked within the specified delay t, fn should be executed with the provided args as arguments.
Example 1:
Input: fn = (x) => x * 5, args = [2], t = 20
Output: [{"time": 20, "returned": 10}]
Explanation:
const cancelTimeMs = 50;
const cancelFn = cancellable((x) => x * 5, [2], 20);
setTimeout(cancelFn, cancelTimeMs);
The cancellation was scheduled to occur after a delay of cancelTimeMs (50ms), which happened after the execution of fn(2) at 20ms.
Example 2:
Input: fn = (x) => x**2, args = [2], t = 100
Output: []
Explanation:
const cancelTimeMs = 50;
const cancelFn = cancellable((x) => x**2, [2], 100);
setTimeout(cancelFn, cancelTimeMs);
The cancellation was scheduled to occur after a delay of cancelTimeMs (50ms), which happened before the execution of fn(2) at 100ms, resulting in fn(2) never being called.
Example 3:
Input: fn = (x1, x2) => x1 * x2, args = [2,4], t = 30
Output: [{"time": 30, "returned": 8}]
Explanation: const cancelTimeMs = 100;
const cancelFn = cancellable((x1, x2) => x1 * x2, [2,4], 30);
setTimeout(cancelFn, cancelTimeMs);
The cancellation was scheduled to occur after a delay of cancelTimeMs (100ms), which happened after the execution of fn(2,4) at 30ms.
Constraints:
fnis a functionargsis a valid JSON array1 <= args.length <= 1020 <= t <= 100010 <= cancelTimeMs <= 1000
题目大意
给定一个函数 fn ,一个参数数组 args 和一个以毫秒为单位的超时时间 t ,返回一个取消函数 cancelFn 。
在 cancelTimeMs 的延迟后,返回的取消函数 cancelFn 将被调用。
setTimeout(cancelFn, cancelTimeMs)
最初,函数 fn 的执行应该延迟 t 毫秒。
如果在 t 毫秒的延迟之前调用了函数 cancelFn,它应该取消 fn 的延迟执行。否则,如果在指定的延迟 t 内没有调用 cancelFn,则应执行 fn,并使用提供的 args 作为参数。
提示:
fn是一个函数args是一个有效的 JSON 数组1 <= args.length <= 1020 <= t <= 100010 <= cancelTimeMs <= 1000
解题思路
创建定时器:使用
setTimeout来执行fn,并设置延迟t毫秒后执行。实现取消功能:
setTimeout会返回一个timer句柄,可以通过clearTimeout(timer)来取消该定时器。返回一个取消函数cancelFn,该函数被调用时会清除定时器,阻止fn的执行。
复杂度分析
- 时间复杂度:
O(1),setTimeout和clearTimeout的调用都是常数时间操作。 - 空间复杂度:
O(1),存储一个定时器句柄timer以及取消函数占用常数空间。
代码
/**
* @param {Function} fn
* @param {Array} args
* @param {number} t
* @return {Function}
*/
var cancellable = function (fn, args, t) {
const timer = setTimeout(() => fn(...args), t); // 延迟 t 毫秒后执行 fn
const cancelFn = () => clearTimeout(timer); // 返回取消函数
return cancelFn;
};
/**
* const result = [];
*
* const fn = (x) => x * 5;
* const args = [2], t = 20, cancelTimeMs = 50;
*
* const start = performance.now();
*
* const log = (...argsArr) => {
* const diff = Math.floor(performance.now() - start);
* result.push({"time": diff, "returned": fn(...argsArr)});
* }
*
* const cancel = cancellable(log, args, t);
*
* const maxT = Math.max(t, cancelTimeMs);
*
* setTimeout(cancel, cancelTimeMs);
*
* setTimeout(() => {
* console.log(result); // [{"time":20,"returned":10}]
* }, maxT + 15)
*/
