More on JavaScript Objects
By Jeff Cogswell
August 16, 2007
I've done a few articles recently about JavaScript. Why? Because as we develop for the web, more and more of our development is moving to the client side. Even for us ASP.NET programmers, we need to know the browser-side language, which is usually JavaScript.
In the previous article, I introduced the notion of a function being an object. Here's the code I finished up with:
function Counter1() {
this.value = 0;
this.increment = function() {
this.value++;
}
}
Counter1 is a function, but inside it creates an internal object. You can refer to the object in the code using the keyword this. When you call the function using the new keyword, you'll get back the same "this" object. Thus, you can do this kind of thing:
obj1 = new Counter1();
obj1.increment();
obj1.increment();
alert(obj1.value);
obj2 = new Counter1();
obj2.increment();
alert(obj2.value);
First I called Counter1 with the new keyword, which resulted in the creation of an object. The code inside the Counter1 function added on (at runtime) a value member and an increment member. The value member is an integer, and the increment member is a function which in turn increments the value. I can reference the value of the object through the this keyword both in the main Counter1 function as well as the newly-created (but unnamed) function stored in the increment variable.
Since I used the new keyword, the object created gets returned and I save it in the obj1 variable. To try it out, I call the object's increment function twice, and then I display the object's value member. (Technically, though, if I want to be precise, I should say that I call the unnamed function stored in the object's increment member.)
Then just to show that I really can create separate objects, I create a second object (which I store in obj2) and try out its members.
Functions stored in variables
Before continuing one, just to make sure you're completely clear on how all this works, make sure you fully understand the difference between these two pieces of code:
function MyFunc() {
alert('hi');
}
and, by comparison, this:
MyFunc2 = function() {
alert('there');
}
The first of these creates a function called MyFunc. The second of these creates a function, but doesn't give it a name, and then stores the function in the MyFunc2 variable. From there, you can call either using MyFunc() and MyFunc2().
Next, think about how a function is, in fact, an object. Consider this code, which uses the preceding MyFunc2 variable:
MyFunc3 = MyFunc2;
MyFunc3.somemember = 10;
alert(MyFunc3.somemember);
This first line of this code copies the value of MyFunc2 to MyFunc3. Since the value of MyFunc2 is the unnamed function, the value of MyFunc3 is this same function. The second line adds a new member to the function called somemember, and sets its value to 10. Although I'm using the MyFunc3 variable to do this, the two variables refer to the same function object. Thus, in the third line, when I do an alert on the MyFunc3 value's somemember, I'll see the 10 that I assigned. Thus, these two variables refer to the same single function object. Changing one changes the "other", since they're both, in fact, the same object.
Now let's continue our discussion. Note: To create the examples for this article, I used FireFox and the FireBug tool, simply because it's easy to quickly try out JavaScript code.
JavaScript and Prototypes
To fully understand the object system, however, it's important to understand the whole architecture behind it. JavaScript uses an approach called a prototype architecture.
First, remember that JavaScript is run line-by-line. Prior to the declaration of the Counter1 function above, the function does not exist. Also remember that nearly everything in JavaScript is an object. Thus, Counter1 is itself an object.
But what type are the objects stored in my obj1 and obj2 variables? Their type is object and nothing more. These objects are not instances of Counter1, although in our own minds it's okay to think of them as such. Counter1 is not a class; rather, it's simply a function that, when used in conjunction with the new keyword, creates a new object.
If you want to give the members to the objects created by the Counter1 function, you can do so inside the Counter1 function, as I did with this line:
this.value = 0;
However, there's another way to do this. Objects in JavaScript can optionally include a member called prototype. This member is itself an object, and as its name implies, it provides a prototype for objects created based on the object.
That's a mouthful, so let's look at an example. Consider the Counter1 function. When you created this function (via the function keyword), you created a function object, which automatically came with a member object called prototype. If you're trying out the code in FireBug, you can inspect this member. Try an alert:
alert(Counter1.prototype)
This will open an alert box displaying the words [object Object], which simply means it's an object. Initially, this object doesn't contain anything. But if you add members to this object, the objects you create by calling new Counter1 will get copies of these members.
Let's try another example with the help of a new function called Counter2. Here's the code:
function Counter2() {
}
Not much there... yet. Follow with this code:
Counter2.prototype.value = 0;
Counter2.prototype.increment = function() {
this.value++;
}
This adds two members to the Counter2 function's prototype object, one called value and one called increment. When you create a new object using the new keyword and calling this Counter2 function, your new object will automatically inherit copies of the members of this prototype. Try it out:
c1 = new Counter2();
c1.increment();
c1.increment();
alert(c1.value);
When the alert box opens, you'll see the value 2; thus, c1 has the value and increment members. In FireBug, you can inspect the object using FireFox's built in dir function:
>>> dir(c1)
value 2
increment function()
But now try inspecting the Counter2 function's prototype object:
>>>dir(Counter2.prototype)
value 0
increment function()
Prototypes are an important part of JavaScript as they provide a handy means by which objects can be given members. Remember, however, the prototype member is just an object itself, a member of the Counter2 object.
Up Next
Next time we'll continue this discussion with objects and you'll see how many things that we think of as built-in types are, in fact, objects themselves. This includes the Function object and the Array object. Once you understand these, you'll be well one your way to processing data in JavaScript. And from there, we'll conclude this series with an introduction to the AJAX.
Source: http://www.devsource.com