Although a JavaScript object literal and a JavaScript instance object are both objects, they differ in their inherent nature and features
Object Literals
An object literal is “flat”. You create it, you add properties and methods to it, and all of those properties and methods are public. You can mutate any members of that object at any time. A JavaScript object literal does not provide any kind of private scope or private variables. Although, any of the members of an object literal an certainly be a function that provides these features. Object literals are useful because they are a lightweight way of providing multidimensional data in a way that is easy to pass around and consume.
Example # 1
var data = {
fname: "foo",
addOne: function(num){ return num + 1}
}
console.log(data.fname)
console.log(data.addOne(4))
data.fname = "bar";
console.log(data.fname)
data.lname = "baz";
console.log(data.lname)
data.say = function(){ return "this is the say function" };
console.log( data.say() );
In example # 1, we have defined a JavaScript object literal and assigned it to the variable “data”. This object has two members; the property “fname” and the method “addOne”. At run time, we can mutate this object very easily and add new properties (i.e. “lame”) and methods (i.e. “say”). The upside is that this object is totally exposed and we can access or mutate any of its members any time we like with no problem (remember though that if an object member is a function, then that function does provide its own private scope and that scope is not accessible to us). The downside of this object is that it does not inherently have a private scope, nor is there the kind of initialization that is provided by a constructor upon creation.
The output for example # 1 is:
foo
5
bar
baz
this is the say function
Instance Objects
An instance object is what is returned when instantiating a JavaScript constructor function, using JavaScript “new” keyword. When you say “var a – new b()”, “a” becomes an “instance” of the fuction “b()”. Any expressions within b() are executed, any local variables in b() are copied and provided in “a”, and the value of “this” inside of “a”, refers to the context inside of “a”. The function “b” is never touched or changed, it simply acts as a “blueprint” for “a”, and “a” is an “instance” of “b”. Any local variables inside of “a” are not accessible outside of “a” and can only be muted by privileged members of “a”.
Example # 2
var Foo = function(){
var _color= "blue";
console.log("welcome to your new instance object");
this.getColor = function(){
return _color;
}
this.setColor = function(newColor){
_color = newColor;
}
}
var bar = new Foo(); // "welcome to your new instance object"
console.log(bar._color); // undefined
console.log(bar.getColor()); // "blue"
bar.setColor("red")
console.log(bar.getColor()); // "red"
In example # 2, we have created a constructor function. A JavaScript constructor function is a function that is not meant to be executed directly, for example we never plan to do the following: “Foo()”. Instead, a constructor is meant to be instantiated. This means that you create an “instance” of that function using the JavaScript “new” keyword. We have created an instance of Foo() by saying “var bar = new Foo()”. We now have a variable named “bar” that is an exact copy of Foo().
What makes “bar” differ from our JavaScript Object Literal that we defined in example # 1, is that when our instance object (“bar”) is created, any execution code in the constructor (i.e. “Foo()” ) runs, and any private variables defined in the constructor remain private in the instance object (i.e. “_color”).
What makes this scenario a little more special than that of the object literal is that we can have privileged methods. These are methods that are made public by the use of the “this” prefix, but they have access to the instance object’s private members (i.e. “_color”). So, when we run this code, the constructor function code runs (“welcome to your new instance object”), we attempt to output the value of “_color”, but “undefined” is returned, becase “_color” is private and cannot be accessed outside of “bar”. We then use the privileged method “getColor()” to get the value of _color the correct way, and “blue” is returned. We then change the value of “_color” using the privileged memer “setColor()”, and return it’s value using “getColor()” again (“red”).
Summary
Both Object Literals and Instance Objects have their place and purpose in JavaScript. The power of Object Literals is in their lightweight syntax and ease of use. The power of instance objects is that they provide private scope and initialization code that runs when they are created.
Helpful links for JavaScript Objects
http://www.w3schools.com/js/js_objects.asp
http://www.javascriptkit.com/javatutors/oopjs.shtml
http://www.dyn-web.com/tutorials/obj_lit.php
http://www.davidpirek.com/blog.aspx?n=JavaScript-Class-Constructor-vs.-Object-Literal:-Difference-in-Implementation-and-Inheritance