#javascript #apply
#javascript #применить
Вопрос:
Кто-нибудь знает, почему в javascript это работает
m = Math.max
m.apply(null, [1,2,3])
но это не так?
m = Math.max.apply
m(null, [1,2,3])
Он выдает исключение:
Ошибка типа: Function.prototype.apply была вызвана для undefined, который является неопределенным, а не функцией
Комментарии:
1. это связано с тем, что вы используете apply перед назначением / добавлением каких-либо значений, поэтому оно не определено перед наличием значений. apply используется при определении значений
Ответ №1:
Согласно спецификации
- Если IsCallable(func) имеет значение false, генерируется исключение TypeError .
func
это объект, для которого apply
вызывается метод.
apply
позволяет указать контекст function
более позднего, который undefined
в вашем случае, поскольку m
не имеет контекста функции (который должен быть указан в аргументах).
Поскольку аргументы
Неперехваченная ошибка типа: Function.prototype.apply была вызвана для undefined, которая является неопределенной, а не функцией
Вы можете проверить это, попробовав следующее
Пример 1:
m = Math.max.apply.bind(this)
m(this, [1,2,3])
Была вызвана неперехваченная ошибка типа: Function.prototype.apply
, которая является объектом, а не функцией
Пример 2:
m = Math.max.apply.bind(null)
m(this, [1,2,3])
Неперехваченная ошибка типа: Function.prototype.apply была вызвана для
null, который является объектом, а не функцией
Пример 3: (Этот не выдает ошибку, поскольку указан контекст функции)
m = Math.max.apply.bind(function(){})
m(this, [1,2,3])
не определено
Пример 4: (Наконец, это дает вам желаемый результат)
m = Math.max.apply.bind(Math.max)
m(this, [1,2,3])
3
Ответ №2:
Чтобы понять, почему второй пример завершается неудачно, вы должны понимать контекст функции в Javascript. В Javascript методы похожи на сообщения, отправляемые объекту, который они вызывают. Объект, который они вызывают, является их контекстом, и, следовательно, этот объект будет значением this
внутри тела функции.
apply
это специальная функция, которая позволяет вам установить этот контекст в качестве первого аргумента, а затем остальные аргументы будут аргументами функции, которая применяется Math.max
в вашем примере. Но в то же время apply
для работы необходимо вызвать объект функции. Во втором примере вы сохраняете в m
переменной ссылку на функцию apply и вызываете ее без контекста, поэтому она завершается с ошибкой, потому что apply не знает, какую функцию он должен вызвать.