JavaScript отличается от того, к чему относится специальное имя this
, чем большинство других языков программирования.Существует ровно пять различных способов, которыми значение this
может быть связано в языке.
Глобальная область действия
this;
При использовании this
в глобальной области он просто будет ссылаться на глобальный объект.
вызов функции
foo();
Здесь this
снова будет ссылаться на глобальный объект.
ES5 Примечание: В строгом режиме глобальный регистр больше не существует .* В этом случае this
будет иметь значение undefined
.
Вызов метода
test.foo();
В этом примере this
будет ссылаться на test
.
Вызов конструктора
new foo();
Вызов функции, которому предшествует ключевое слово new
, действует как конструктор.Внутри функции this
будет ссылаться на вновь созданный Object
.
Явный параметр this
function foo(a, b, c) {}
var bar = {};
foo.apply(bar, [1, 2, 3]); // array will expand to the below
foo.call(bar, 1, 2, 3); // results in a = 1, b = 2, c = 3
При использовании call
или apply
методов Function.prototype
, значение this
внутри вызываемой функции получает , явно устанавливающее в качестве первого аргумента соответствующего вызова функции.
В результате вВ приведенном выше примере метод не не применяется, и this
внутри foo
будет установлен на bar
.
Примечание: this
нельзя использовать для ссылки на объект внутри литерала Object
.Таким образом, var obj = {me: this}
будет не в результате me
, ссылаясь на obj
, поскольку this
связывается только с одним из пяти перечисленных случаев.
Распространенные ловушки
Хотя большинство этих случаев имеет смысл, первый из них следует считать еще одним неправильным дизайном языка, поскольку он никогда не имеет практического применения.
Foo.method = function() {
function test() {
// this is set to the global object
}
test();
}
Распространенным заблуждением является то, что this
внутри test
относится к Foo
;в то время как на самом деле не .
Чтобы получить доступ к Foo
из test
, необходимо создать локальную переменную внутри method
, которая ссылается наFoo
.
Foo.method = function() {
var that = this;
function test() {
// Use that instead of this here
}
test();
}
that
- это просто обычное имя переменной, но оно обычно используется для ссылки на внешний this
.В сочетании с замыканиями его также можно использовать для передачи this
значений.
Назначение методов
Еще одна вещь, которая не работает в JavaScript, - это псевдонимы функций, присваивая метод переменной.
var test = someObject.methodTest;
test();
Из-за первого случая test
теперь действует как простой вызов функции;следовательно, this
внутри него больше не будет ссылаться на someObject
.
Хотя позднее связывание this
на первый взгляд может показаться плохой идеей, на самом деле именно это и делает работу наследования прототипов.
function Foo() {}
Foo.prototype.method = function() {};
function Bar() {}
Bar.prototype = Foo.prototype;
new Bar().method();
Когда method
вызывается для экземпляра Bar
, this
теперь будет ссылаться на этот самый экземпляр.
Отказ от ответственности: Бесстыдно похищен из моих собственных ресурсов в http://bonsaiden.github.com/JavaScript-Garden/#function.this