Переопределить функцию (например, "предупреждение") и вызвать исходную функцию?
Я хотел бы переопределить встроенную функцию Javascript с новой версией, которая вызывает оригинал (аналогично переопределению метода в классе с версией, которая вызывает super
на многих языках). Как я могу это сделать?
Например...
window.alert = function(str) {
//do something additional
if(console) console.log(str);
//super.alert(str) // How do I do this bit?
}
Ответы
Ответ 1
Сохраните ссылку на исходную функцию в переменной:
(function() {
var _alert = window.alert; // <-- Reference
window.alert = function(str) {
// do something additional
if(console) console.log(str);
//return _alert.apply(this, arguments); // <-- The universal method
_alert(str); // Suits for this case
};
})();
Универсальный способ <original_func_reference>.apply(this, arguments)
- сохранить контекст и передать все аргументы. Обычно возвращаемое значение исходного метода также должно быть возвращено.
Однако он знал, что alert
является функцией void, принимает только один аргумент и не использует this
объект. Итак, _alert(str)
достаточно в этом случае.
Примечание. IE <= 8 выдает ошибку, если вы пытаетесь перезаписать alert
, поэтому убедитесь, что вы используете window.alert =...
вместо alert =...
Ответ 2
Нет "супер". Во всяком случае, создайте закрытие, чтобы "сохранить" вокруг исходного объекта функции.
Обратите внимание на функцию "self invoking", которая возвращает новый объект-объект (которому присвоено свойство window.alert
). Новый возвращаемый объект-функция создает замыкание вокруг original
переменной, которое вычисляет исходное значение window.alert
которое было передано в функцию "self invoking".
window.alert = (function (original) {
return function (str) {
//do something additional
if(console) {
console.log(str)
}
original(str)
}
})(window.alert)
Тем не менее, я считаю, что некоторые браузеры могут предотвратить изменение alert
и других встроенных модулей...
Счастливое кодирование.
Ответ 3
Я предполагаю, что ваш вопрос заключается в том, как вы перезаписываете встроенный и все еще можете его назвать. Прежде всего, как отказ от ответственности, вы никогда не должны перезаписывать встроенные вложения, если у вас нет веских оснований для этого, поскольку это сделает невозможным отладки/тестирование.
Вот как вы это сделаете:
window._alert = window.alert;
window.alert = function(str) {
if(console) console.log(str);
window._alert(str);
}
Ответ 4
Как сделать простое классическое наследование в Javascript:
SuperClass.call(this) // inherit from SuperClass (multiple inheritance yes)
Как переопределить функции:
this.myFunction = this.myFunction.override(
function(){
this.superFunction(); // call the overridden function
}
);
Функция переопределения создается следующим образом:
Function.prototype.override = function(func)
{
var superFunction = this;
return function()
{
this.superFunction = superFunction;
return func.apply(this,arguments);
};
};
Работает с несколькими аргументами.
Сбой при попытке переопределить неопределенные или нефункции.
Делает "суперфункцию" "зарезервированным" словом :-)
Ответ 5
JavaScript не использует классическую модель наследования. Здесь есть хорошая статья, в которой описывается способ написания ваших классов, чтобы можно было использовать аналогичный синтаксис, но он не поддерживается.