Javascriptthis keyword use analytics_javascript skills

Source: Internet
Author: User
This is the definition of this in www.quirksmode.orgjsthis.html. It seems that the definition does not know anything. The following uses examples to describe the objects and principles of this in various situations. I have read many articles about the this keyword in js. I wrote this article to analyze the working principle of this from an instance and hope it will be helpful to you.

I. Basic:

The Code is as follows:


Function doSomething (){
Alert (this. id );
}
Alert (window. doSomething); // proves that doSomething belongs to window.
DoSomething (); // undefined
Window. onload = function (){
Document. getElementById ("p2"). onclick = doSomething; // p2
Document. getElementById ("p3"). onclick = function () {doSomething ();} // undefined
}


1. For the doSomething function:

The Code is as follows:


Function doSomething (){
Alert (this. id );
}


This function is a global function, which actually belongs to the window (you can use window. doSomething to access). If you call this function directly, then according to "this always refers to the" owner "of the function we're re executing", then this in the function is window, however, the window does not have the id attribute, so "undefined" is displayed ";

2. Calling in html elements like this

The Code is as follows:


P1




"Undefined" is displayed, which is equivalent to the following code:

The Code is as follows:


Document. getElementById ("p1"). onclick = function () {doSomething ();}


When you click p1, The doSomething function of the window is called, so "undefined" is displayed ";

3. Bind events through js. After p2 is loaded:

The Code is as follows:


Document. getElementById ("p2"). onclick = doSomething;


When p2 is clicked, "p2" is displayed. Because doSomething is copied once when an onclick value is assigned to p2, the copied function belongs to p2, it has nothing to do with doSomething of window. When you click p2, The doSomething of p2 will be triggered. Here this refers to p2.

2. attachEvent and addEventListener

AttachEvent is the method for binding events in ie. It copies the corresponding function to the global (that is, the owner of the response function is window), but in the DOM standard, the owner of the Response Function copied when the addEventListener is bound to an event is the object bound to the event.

The Code is as follows:


Function doSomething (){
Alert (this. id );
Alert (this = window );
}
Window. onload = function (){
Var p1 = document. getElementById ("p1 ");
If (p1.attachEvent ){
P1.attachEvent ("onclick", doSomething );
Document. body. appendChild (document. createTextNode ("attachEvent "));
} Else if (p1.addEventListener ){
P1.addEventListener ("click", doSomething, false );
Document. body. appendChild (document. createTextNode ("addEventListener "));
} Else {
P. onclick = doSomething;
}
}



For the function doSomething

The Code is as follows:


Function doSomething (){
Alert (this. id );
Alert (this = window );
}


1. Use attachEvent to bind to the click event of p1, and doSometing will be copied to the window. this in doSomething indicates the window. When you click p1, "undefined" and "true" will be displayed"

2. Use addEventListener to bind the click event of p1, and copy doSomething. The copied function belongs to p1. Therefore, "p1" and "false" are displayed when you click p1"

Note: accept:

The Code is as follows:


Var obj = new Object ();
Obj. color = "black ";
Obj. showColor = function (){
Alert (this. color );
Alert (this = window );
}
Obj. showColor ();

Var p1 = document. getElementById ("p1 ");
P1.attachEvent ("onclick", obj. showColor );


When you click p1, "undefined" and "true" are displayed. If attachEvent only references obj. if showColor is used, this should still refer to obj, but in fact this refers to window, so I think this is not a reference, but a copy to the global one.

Iii. Inheritance methods of object impersonating

1. Differences between new and non-new

For the following functions

The Code is as follows:


Function ClassA (sColor ){
This. color = sColor;
This. sayColor = function (){
Alert (this. color );
}
}


Is this a class or a function? Depends on you!

If you think this is a function, we can call it like this:

ClassA ("red ");
"Red" is a passed parameter. this in ClassA refers to the window of course, so now window has the color attribute and sayColor method, and color has the value "red.

This is to call sayColor or window. sayColor to display "red ";

Window. sayColor ();


If you think this is a class, we should use it like this:

Var obj = new ClassA ("red ");
The emergence of the keyword "new" adds a lot of content to the above Code: first, create an Object instance, and then point this in ClassA to the created Object, finally, this Object is returned, so the returned Object is assigned to obj. So we can say that this points to obj. obj has the color attribute and sayColor method, and the color attribute value is "red ".

2. Function owener

The Code is as follows:


Function showId (){
Alert (this. id );
}
Window. onload = function (){
Var p1 = document. getElementById ("p1 ");
P1.onclick = showId;
P1.show = showId;
P1.show ();

Var obj = new Object ();
Obj. id = "obj ";
Obj. show = showId;
Obj. show ();
}


We can assign the showId function to the click event, or assign a value to any attribute of any object. This will also copy the showId method, so when we call the p1.show method, this indicates p1. When you call obj. show, this points to obj.

3. Object impersonating Principle

The following code is the inheritance implemented through the object impersonating method.

The Code is as follows:


Function ClassA (sColor ){
This. color = sColor;
This. sayColor = function (){
Alert (this. color );
}
}

Function ClassB (sColor, sName ){
This. newMethod = ClassA;
This. newMethod (sColor );
Delete this. newMethod;

This. name = sName;
This. sayName = function (){
Alert (this. name );
}
}

Var objB = new ClassB ("color of objB", "name of objB ");
ObjB. sayColor ();


ObjB is an example of ClassB. How does objB possess the color attribute and the sayColor method?

First, we can see from the instantiated code:

Var objB = new ClassB ("color of objB", "name of objB ");

Here ClassB is a class, and this in ClassB is of course the objB object;

In ClassB, ClassA is used for the first three lines of code. In this case, ClassA is regarded as a function rather than a class.

If we call the ClassA function directly, it is clear that this in ClassA refers to the window object, so we first copy ClassA to the newMethod attribute of objB (this. newMethod = ClassA ),

Then call this. newMethod, this Is The owener of this method, and this in ClassB currently refers to objB, so in ClassA (strictly in newMethod, because this is copied, and ClassA is already two methods.) this refers to objB. In this way, the color attribute and sayColor method are assigned to objB through newMethod. Using the call and apply methods to implement inheritance is actually a principle. call and apply can be seen as the owner Method for changing methods, the first three sentences in ClassB serve this purpose.

4. Class. create in prototype1.6

The Code is as follows:


The Class. create method in prototype1.6 is roughly as follows:

Var Class = {
Create: function (){
//

Function klass (){
This. initialize. apply (this, arguments );
}

//

For (var I = 0; I <properties. length; I ++)
Klass. addMethods (properties [I]);

//

Return klass;
}
};


This is the case when using:


The Code is as follows:


Var Person = Class. create ({
Initialize: function (name ){
This. name = name;
},
Say: function (message ){
Alert (this. name + ":" + message );
}
});

Var aPerson = new Person ("name1 ");
APerson. say ("hello1 ");


The Person actually uses the Class. the klass returned by the create method (klass is a Class. the local variable in create is a function), Class. the parameters (initialize and say methods) passed by create are passed to the properties array in the create method and the klass prototype has these methods through the addMethods method. So the most important thing is what is hard to understand: What is this in klass. If you think about it, it is not difficult to get the answer. Person is actually a klass, and we use the new Keyword when instantiating the Person object:

Var aPerson = new Person ("name1 ");

This is equivalent

Var aPerson = new klass ("name1 ");

Although klass cannot be accessed outside, it can easily explain the problem. klass is a class rather than a simple function (we think so, because the new keyword is used ), this in klass refers to the declared instance. Here it is aPerson. aPerson can use the prototype of klass to own the initialize and say methods. In the new process, the code in klass will also be executed, so initialize will be executed during instantiation, that is, the constructor. (In klass, both this refer to aPerson. Why do I need to call it once through apply? This is mainly to pass the parameters of the constructor. You can use the apply method to Easily upload a number of parameters to the initialize method through arrays .)

5. analyze several examples

I will analyze the examples in other articles:

1. Run the following code:

The Code is as follows:


Function OuterFoo (){
This. Name = 'outer name ';

Function InnerFoo (){
Var Name = 'inner name ';
Alert (Name + ',' + this. Name );
}
Return InnerFoo;
}
OuterFoo ()();


The displayed result is "Inner Name, Outer Name"

OuterFoo is a function (not a class), so the first sentence

This. Name = 'outer name ';

This indicates the window object, so window. Name = 'outer name' after OuterFoo ';

And return InnerFoo. At this time, InnerFoo is also a function (not a class). When InnerFoo is executed, this also refers to window, so this in InnerFoo. the value of Name is "Outer Name" (window. name acts as a transfer station, allowing OuterFoo to pass the "Outer Name" value to InnerFoo), and the value of Name is the local variable "Inner Name"

2. Run the following code:


The Code is as follows:


Function JSClass (){

This. m_Text = 'pision element ';
This. m_Element = document. createElement ('div ');
This. m_Element.innerHTML = this. m_Text;

If (this. m_Element.attachEvent)
This. m_Element.attachEvent ('onclick', this. ToString );
Else if (this. m_Element.addEventListener)
This. m_Element.addEventListener ('click', this. ToString, false );
Else
This. m_Element.onclick = this. ToString;
}

JSClass. prototype. Render = function (){
Document. body. appendChild (this. m_Element );
}

JSClass. prototype. ToString = function (){
Alert (this. m_Text );
Alert (this = window );
}

Window. onload = function (){
Var jc = new JSClass ();
Jc. Render ();
Jc. ToString ();
}


Click "pision element" to display "undefined", "true" under ie, and "false" in other browsers ".

There is nothing to say about the instance declaration and call method. If the click event of an element is bound to an instance method, the method bound to it through addEventListener is copied, therefore, this indicates an html element. this element does not have the m_Text attribute (m_Text belongs to the JSClass instance, that is, the m_Text attribute belongs to jc). Therefore, click the element to display undefined, events bound to attachEvent will copy the function to the global state. this indicates the window object, and "undefined" will be displayed when you click an element ". Only when the jc. ToString () method is called, this indicates the jc object. Because jc has m_Text, "pision element" can be displayed ".

Vi. Summary

In a code environment, how can I quickly find the object referred to by this? I want to pay attention to the following three aspects:
1. You must be clear about whether to copy or reference each function step (CALL)
2. Clearly know what the function owner is.
3. For a function, we need to figure out whether to use it as a function or as a class.

Supplement:
1. functions can be directly defined on instances and classes.
2. You cannot use prototype to define a function on an instance. You can only use prototype to define a function on a class.
3. functions directly defined on the class cannot use this to access the attributes of the object.
4. this can be used for functions created on the prototype of the class. this can be used for functions defined within the class, and the amount of functions created on the object instance can be this

The Code is as follows:


Window. alert = function (msg)
{
Document. write (msg +"
");
}
Function say ()
{
This. f = "props ";
This. func3 = function () {alert ("f3," + this. f );}
}
Say. func1 = function () {alert ("func1," + this. f) ;}; // Error, a function defined directly on the class, cannot use this
Say. prototype. func2 = function () {alert ("func2," + this. f );}
Say. func1 ();
(New say (). func2 ();
Say. func2 (); // Error, a function defined by prototype must be instantiated before an object can be called.
Say. func3 (); // Error, a function defined on the class must be instantiated before it can be called.
(New say (). func3 ();
Var obj = {
Fld1: 10,
Func1: function (msg) {alert (msg );},
Func4: function () {alert (this. fld1 );}
}
Obj. prototype. func = function () {alert ("func") ;}; // prototype cannot be used to define objects in the Error instance.
Obj. func2 = function () {alert ("func2," + this. fld1) ;}; // OK, the function defined on the instance can use this to access the attributes of the object.
Alert (obj. fld1 );
Obj. func1 ("func1 ");
Obj. func2 ();
Obj. func4 ();


Javascript this usage Summary
Http://www.jb51.net/article/16863.htm

JavaScript this in-depth understanding
Http://www.jb51.net/article/19425.htm

Javascript this details object-oriented
Http://www.jb51.net/article/17584.htm

Javascript this pointer
Http://www.jb51.net/article/19434.htm

How to use this keyword in JavaScript
Http://www.jb51.net/article/7954.htm

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.