How does jQuery hijack "this"?
I'm just curious to know how jQuery is able to hijack the 'this' keyword in Javascript. From the book开发者_JAVA百科 I'm reading: "Javascript the Definitive Guide" it states that "this" is a keyword and you cannot alter it like you can with an identifier.
Now, say you are in your own object constructor and you make a call to some jQuery code, how is it able to hijack this from you?
function MyObject(){
// At this point "this" is referring to this object
$("div").each(function(){
// Now this refers to the currently matched div
});
}
My only guess would be that since you are providing a callback to the jQuery each() function, you are now working with a closure that has the jQuery scope chain, and not your own object's scope chain. Is this on the right track?
thanks
You can change the context of a function (i.e. the this
value) by calling it with .call()
or .apply()
and passing your intended context as the first argument.
E.g.
function fn() {
return this.foo;
}
fn.call({foo:123}); // => 123
Note: passing null
to either call
or apply
makes the context the global
object, or, in most cases, window
.
It's probably worth noting the difference between .apply()
and .call()
. The former allows you to pass a bunch of arguments to the function it's being applied to as an array, while the latter lets you just add them as regular arguments after the context argument:
someFunction.apply( thisObject, [1,2,3] );
someFunction.call( thisObject, 1, 2, 3 );
From the jQuery source:
for ( var value = object[0];
i < length &&
callback.call( value, i, value ) // <=== LOOK!
!== false;
value = object[++i] ) {}
It doesn't hijack anything - it just makes sure that "this" is pointing at what it wants it to. Look up the standard "call" function that's available for any Javascript function object.
See the documentation for Function.apply
. The first parameter is the "context". It can be any object. If null, it will be scoped globally.
The function
type in JavaScript has a method called apply()
which allows you to specify to what object this
is bound at. Its signature is:
apply(thisObj, arguments);
Once called, it calls the function binding this
to thisObj
and passing the arguments arguments
.
It is usually used as such:
function product(name, value)
{
this.name = name;
if (value > 1000)
this.value = 999;
else
this.value = value;
}
function prod_dept(name, value, dept)
{
this.dept = dept;
product.apply(this, arguments);
}
prod_dept.prototype = new product();
// since 5 is less than 1000 value is set
var cheese = new prod_dept("feta", 5, "food");
// since 5000 is above 1000, value will be 999
var car = new prod_dept("honda", 5000, "auto");
try this:
var MyObject = { "Test": "Hello world!" };
(function ()
{
alert(this.Test); // Gives "Hello world!"
}).call(MyObject);
(function ()
{
alert(this.Test); // Gives "Hello world!"
}).apply(MyObject);
(function ()
{
alert(this.Test); // Gives "undefined"
})()
function.apply() and function.call() allow you to change what this
points to in Javascript. Here's a couple of handy articles that explain it in greater detail - Scope In Javascript and Binding Scope in Javascript
精彩评论