mak_ufo
@mak_ufo

Почему такое странное поведение у JS?

Здравствуйте. Постараюсь кратко описать проблему. Есть класс:
class RedisAPI {
    constructor(redis) {
        this.masterID = new Array(); //здесь хранятся уникальные ID всех воркеров
        this.master = redis.createClient();
    }

    addWorker(id) {
        this.masterID.push(id);
        console.log(`Worker ${id} is working!`);
    }

    //отправление сообщения на обработку одному из воркеру
    emit() {
        let needID = this.masterID.splice(0, 1);
        console.log(`arr: ${this.masterID.length}; first: ${needID[0]}`);
        this.masterID.push(needID[0]);
    }

    //отправление сообщения на обработку одному из воркеров каждые ms секунд
    emitTimeout(ms) {
        setInterval(() => {
            this.emit();
        }, ms);
    }
}


После двух асинхронных добавления данных в RedisAPI.masterID код начинает себя странно вести, а именно:
const queue = new RedisAPI(redis);
queue.emitTimeout(1000);


А в консоли вижу:
arr: 1; first: undefined
arr: 1; first: id1499261061279
arr: 1; first: undefined
arr: 1; first: id1499261061279

И так чередуется. То есть не получается грамотно удалить первый элемент масиива, хотя он всегда есть. В чём может быть проблема?
  • Вопрос задан
  • 331 просмотр
Пригласить эксперта
Ответы на вопрос 2
//отправление сообщения на обработку одному из воркеру
    emit() {
        let length = this.masterID.length;
        let needID = this.masterID.splice(0, 1);
        console.log(`arr: ${length}; first: ${needID[0]}`);
        this.masterID.push(needID[0]);
    }
Ответ написан
lazalu68
@lazalu68
Salmon
Это вот зачем всё?

let needID = this.masterID.splice(0, 1);
...
this.masterID.push(needID[0]);


Вы этим алгоритмом первый элемент ставите на последнее место. Если бы я не знал задачи, я бы вам сказал "зачем так сложно, делайте просто this.masterID.reverse()". К тому же вы нигде не проверяете пустая ли очередь, в любом случае делаете ваше тёмное дело.

С проверкой всё работает без фокусов
class RedisAPI {
    constructor() {
        this.masterID = new Array(); //здесь хранятся уникальные ID всех воркеров
    }

    addWorker(id) {
        this.masterID.push(id);
        console.log(`Worker ${id} is working!`);
    }

    //отправление сообщения на обработку одному из воркеру
    emit() {
        if (this.masterID.length) {
            let needID = this.masterID.splice(0, 1);
            console.log(`arr: ${this.masterID.length}; first: ${needID[0]}`);
            this.masterID.push(needID[0]);
        } else {
            console.log('The queue is empty!');
        }
    }

    //отправление сообщения на обработку одному из воркеров каждые ms секунд
    emitTimeout(ms) {
        setInterval(() => {
            this.emit();
        }, ms);
    }
}

var queue = new RedisAPI();

queue.emitTimeout(1000);

setTimeout(function() {
    queue.addWorker(42);
}, 1500);
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы