Skip to content

2637. Promise Time Limit

Posted on:April 20, 2023 at 05:00 PM

2637. Promise Time Limit


Given an asynchronous function fn and a time t in milliseconds, return a new time limited version of the input function.

A time limited function is a function that is identical to the original unless it takes longer than t milliseconds to fulfill. In that case, it will reject with "Time Limit Exceeded". Note that it should reject with a string, not an Error.

Example 1.

Input:
fn = async (n) => {
  await new Promise(res => setTimeout(res, 100));
  return n * n;
}
inputs = [5]
t = 50
Output: {"rejected":"Time Limit Exceeded","time":50}
Explanation:
The provided function is set to resolve after 100ms. However, the time limit is set to 50ms. It rejects at t=50ms because the time limit was reached.

Example 2

Input:
fn = async (n) => {
  await new Promise(res => setTimeout(res, 100));
  return n * n;
}
inputs = [5]
t = 150
Output: {"resolved":25,"time":100}
Explanation:
The function resolved 5 * 5 = 25 at t=100ms. The time limit is never reached.

Example 3

Input:
fn = async (a, b) => {
  await new Promise(res => setTimeout(res, 120));
  return a + b;
}
inputs = [5,10]
t = 150
Output: {"resolved":15,"time":120}
Explanation:
The function resolved 5 + 10 = 15 at t=120ms. The time limit is never reached.

Approach

I struggled a little bit understanding this problem.

So, I had to look for the solutions to understand how I was supposed to approach this problem.

Let’s look at the cases first.

Firstly, we should have our own timeout promise function with error message like code below

const timeoutPromise = new Promise((_, reject) => {
  return setTimeout(() => {
    reject(errorMessage);
  }, t);
});

This function will send out reject message once, given time t has passed.

Promise.race()

This Promise.race() was the key of this problem. The Promise.race() method is one of the promise concurrency methods. It’s useful when you want the first async task to complete, but do not care about its eventual state (i.e. it can either succeed or fail).

like it says they race and if timeoutPromise function is executed then it shows reject message before the normal promises ( fn(...args) )

How i Solved the Problem

/**
 * @param {Function} fn
 * @param {number} t
 * @return {Function}
 */
var timeLimit = function (fn, t) {
  const errorMessage = 'Time Limit Exceeded';
  const timeoutPromise = new Promise((_, reject) => {
    return setTimeout(() => {
      reject(errorMessage);
    }, t);
  });

  return async function (...args) {
    const promises = fn(...args);

    return await Promise.race([promises, timeoutPromise]);
  };
};

/**
 * const limited = timeLimit((t) => new Promise(res => setTimeout(res, t)), 100);
 * limited(150).catch(console.log) // "Time Limit Exceeded" at t=100ms
 */