Анализ одностороннего асинхронного вопроса

JavaScript

предисловие

Я не мог написать этот вопрос для интервью в то время. В то время я хвастался, что знаком с промисами. Было немного неловко писать этот вопрос. Это.

Последующее собеседование не было завершено, потому что стажер дропа уже был нанят до собеседования.

тема

//JS实现一个带并发限制的异步调度器Scheduler,保证同时运行的任务最多有两个。完善代码中Scheduler类,使得以下程序能正确输出
class Scheduler {
  add(promiseCreator) { ... }
  // ...
}

const timeout = (time) => new Promise(resolve => {
  setTimeout(resolve, time)
})

const scheduler = new Scheduler()
const addTask = (time, order) => {
  scheduler.add(() => timeout(time))
    .then(() => console.log(order))
}

addTask(1000, '1')
addTask(500, '2')
addTask(300, '3')
addTask(400, '4')
// output: 2 3 1 4

// 一开始,1、2两个任务进入队列
// 500ms时,2完成,输出2,任务3进队
// 800ms时,3完成,输出3,任务4进队
// 1000ms时,1完成,输出1
// 1200ms时,4完成,输出4

рабочий процесс

Левое значение @ — это оставшееся время, а правое значение — это выходное содержимое.

Очередь выполнения (максимум две) очередь ожидания поведение содержание исполнения
1000@1 Если очередь выполнения не заполнена, войдите в очередь выполнения напрямую. addTask(1000, '1')
1000@1, 500@2 Если очередь выполнения не заполнена, войдите в очередь выполнения напрямую. addTask(500, '2')
1000@1, 500@2 300@3 Очередь выполнения заполнена, присоединяйтесь к очереди ожидания addTask(300, '3')
1000@1, 500@2 300@3, 400@4 Очередь выполнения заполнена, присоединяйтесь к очереди ожидания addTask(400, '4')
500@1, 300@3 400@4 500@2 выполняется и выводит 2, 1000@1 потребляет 500 и добавляется в очередь выполнения по порядку из очереди ожидания
200@1, 400@4 Выполнение 300@3 завершает вывод 3, 500@1 потребляет 300 и добавляется в очередь выполнения по порядку из очереди ожидания
200@4 200@1 завершение выполнения, выход 1
200@4 выполнение завершено, выход 4

идеи

Обратите внимание, что то, что передается в методе добавления, является функцией и возвращает обещание. Это сложный момент. Многие люди меняют вопрос. Я видел, как он написан с помощью геттеров и сеттеров. Я думаю, что это отличается от предмета, который нужно протестировать. .

С первыми двумя легко справиться, напрямую определить, заполнена ли очередь выполнения, и напрямую войти в очередь, если она не заполнена.

Для третьего и более поздних вам нужно судить, разрешены ли первые два.Обратите внимание, что концепции первых двух и первых двух различаются (поскольку это уровень абстракции, вот пример: в настоящее время в третьем, затем первое из первых двух относится к первому к первому, последнее относится ко второму; в настоящее время в четвертом, затем первое из первых двух относится к первому ко второму, последнее относится к третьему; и и т. д.), после разрешения Добавить в очередь выполнения по порядку из очереди ожидания.

Этому есть две причины. Первое выполняется первым, то есть все задачи в коллекции выполнены, затем вторые обязательно поступают в исполнение (незавершенные), затем в очереди на выполнение остается позиция; вторые завершаются первыми, остается нечего сказать об этом, последнее Обязательно останется одно место, когда вы закончите.

код

class Scheduler {
    constructor() {
        this.list=[]   //promise list
        this.cur=0   //current position
        this.max=2
    }
    add(promiseCreator) {
        let temp=null;

        if(this.cur < this.max) {
            temp=promiseCreator();
        }else {
            let arr=this.list.slice(0,this.cur-1);
            let all=Promise.all(arr);
            
            temp=Promise.race([all,this.list[this.cur-1]])
                    .then(() => {
                        return promiseCreator();
                    });
        }

        this.list.push(temp);
        this.cur++;
        return temp;
    }
}

Слабые стороны и слабости

  • нельзя использовать повторно

    Если максимальное количество очередей выполнения настроено на 3 или более, необходимо определить, есть ли разрешение в первых n

  • склонность к взрыву памяти

    Список всегда выполнял обещания, будь то решенные или ожидающие решения.

  • Обработка исключений

Вопросы в разделе комментариев

В принципе, идеи всех областей комментариев схожи. Кроме того, есть тот факт, что большинство людей не рассматривали проблему с данными исходного обещания (найденного старшими), если оно действительно применяется, это должны быть данные, хотя в исходном вопросе об этом не упоминалось.

наконец

Если у вас есть другие идеи или идеи для недостатков, пожалуйста, прокомментируйте