Параметры функции setTimeout не определены (JS) - PullRequest
0 голосов
/ 08 мая 2020

Мне не удалось найти правильного объяснения этому.

function subtract(x, y) {
    setTimeout(function(x, y) {
      document.write(x - y);
  }, 1000);
}

subtract(1, 1);

Это записывает NaN в документ, потому что параметры x и y, переданные в setTimeout, не определены. Вы могли бы подумать, что x и y должны быть целыми числами 1 и находятся в пределах функции вычитания. Следующий фрагмент отлично работает и записывает целое число 0, как и ожидалось:

function subtract(x, y) {
    setTimeout(function() {
      document.write(x - y);
  }, 1000);
}

subtract(1, 1);

Удаление параметров, похоже, решает проблему. Почему?

Ответы [ 3 ]

1 голос
/ 08 мая 2020

Вы не передали параметры в обратный вызов функции, когда обратный вызов в конечном итоге вызывается setTimeout, x и y равны undefined.

Итак, вы видите NaN в качестве вывода, потому что undefined - undefined равно NaN.

setTimeout принимает параметры обратного вызова функции, которые вы передали после аргумента delay, в вашем случае после 1000.

Без передачи параметров переменные x и y привязаны к функции обратного вызова. Он не будет принимать значения из внешней области видимости, поскольку она затенена заданными вами параметрами функции.

function subtract(x, y) {
    setTimeout(function(x, y) {
      document.write(x - y);
  }, 1000, 1, 1);
}

subtract(1, 1);

Вы также можете использовать Function.prototype.bind для передачи параметров функции обратного вызова.

bind принимает контекст this в качестве первого аргумента, а остальные аргументы являются параметрами функции. В моем примере я дал null как контекст this:

function subtract(x, y) {
    setTimeout(function(x, y) {
      document.write(x - y);
  }.bind(null,1,1), 500);
}

subtract(1, 1);
0 голосов
/ 08 мая 2020

Это из-за замыканий, асинхронных функций и контекста выполнения. settimeout - это асинхронная функция, что означает, что она не ожидает и не блокирует выполнение. Функция Settimeout выполняется по событию l oop tick. Если вы не передаете в него аргументы функции, тогда он включает значения из функции вычитания и сохраняет их для использования во время выполнения. Это из-за концепции закрытия. В случае, если мы передаем аргументы, он больше не ведет себя как закрытие и ожидает аргументов во время выполнения, которое является нулевым. Итак, вы получаете NaN. Для эксперимента передайте аргументы по умолчанию функции в settimeout и проверьте.

0 голосов
/ 08 мая 2020

Это javascript справочная проблема https://developer.mozilla.org/en-US/docs/Web/API/WindowOrWorkerGlobalScope/setTimeout

В разделе «Эта» проблема упоминается та же проблема

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...