Использование объектов JavaScript в качестве «хранилища функций» и их динамический вызов? - PullRequest
0 голосов
/ 03 января 2019

Рассмотрим что-то вроде этого:

const keyAction = {
    a() {
        console.log("You've pressed 'a'");
    },
    b() {
        console.log("You've pressed 'b'");
    },
    c() {
        console.log("You've pressed 'c'");
    }
}

document.addEventListener('keydown', e => keyAction[e.key]());

Это плохая практика?Есть ли причина не делать это таким образом?

Ответы [ 3 ]

0 голосов
/ 03 января 2019

Использование объекта в качестве хранилища функций - неплохая идея. Это легко понять, легко поддерживать и быстро получить доступ к (из-за системы хэш-карт) . Это также позволяет вам обрабатывать ваши данные по сравнению с вещами if / else if / ... - например, выполнять цикл ... ect

В зависимости от того, что вы пытаетесь сделать, это может быть хорошей помощью.

Старайтесь избегать воссоздания объекта каждый раз, когда вы вызываете функцию tho. Постройте его один раз и используйте повторно.

const keyAction = {
  a: () => {
    console.log("You've pressed 'a'");
  },

  b: () => {
    console.log("You've pressed 'b'");
  },
};

function clickFunc(key) {
  keyAction[key]();
}
.ex {
  background-color: #444444;
  color: white;
  height: 5em;
  width: 5em;
  margin: 1em;
  cursor: pointer;
  display: flex;
  flex-direction: row;
  align-items: center;
  justify-content: center;
}
<div class="ex" onclick="clickFunc('a')">
  A
</div>

<div class="ex" onclick="clickFunc('b')">
  B
</div>
0 голосов
/ 03 января 2019

У вас есть проблема, когда вы нажимаете клавишу, которую вы не обработали, вы увидите Error: keyAction[e.key] is not a function

if (typeof keyAction[e.key] === 'function') {
    return keyAction[e.key]()
}

console.log('You pressed a some button')

Javascript - это динамический язык, конечно, для некоторых случаев он очень хорош. Но не нужно злоупотреблять, потому что вы можете потерять контроль быстрее, чем можете себе представить

0 голосов
/ 03 января 2019

На самом деле это популярная практика, поскольку некоторые люди, как правило, используют объекты для имитации пространств имен из других языков. Я думаю, в этом нет ничего плохого, если вы понимаете ловушки, которые может создать этот подход. Например, вы должны помнить, что происходит с this при передаче этих функций в качестве параметров (см. Пример ниже):

const store = {
    a() {
        this.b();
    },
    b() {
        console.log("It works!");
    }
}

store.a();  // Logs "It works"
setTimeout(store.a, 10) // Error: this.b is not a function

Также, как заметил @Nick Ovchinnikov, в вашем конкретном примере есть еще один подводный камень. Вы должны убедиться, что при каждом нажатии кнопки среда не будет пытаться вызвать функцию, которая не существует, иначе вы можете столкнуться с ошибкой. В итоге привязка вашего обработчика должна выглядеть примерно так:

document.addEventListener('keydown', e => {
    if (typeof keyAction[e.key] === 'function') {
        keyAction[e.key]();
    }
});
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...