Design Patterns
Download - Assembla
Download - Assembla
- No tags were found...
You also want an ePaper? Increase the reach of your titles
YUMPU automatically turns print PDFs into web optimized ePapers that Google loves.
CHAPTER 4 ■ INHERITANCE 47<br />
attribute set to the prototype object. When it is just created, author[1].name is actually a link<br />
back to the primitive Person.name. This is because of the asymmetry inherent in reading and<br />
writing objects linked from the prototype. When you read the value of author[1].name, you are<br />
getting the value linked from the prototype, provided you haven’t defined the name attribute<br />
directly on the author[1] instance yet. When you write to author[1].name, you are defining<br />
a new attribute directly on the author[1] object.<br />
This example illustrates that asymmetry:<br />
var authorClone = clone(Author);<br />
alert(authorClone.name); // Linked to the primative Person.name, which is the<br />
// string 'default name'.<br />
authorClone.name = 'new name'; // A new primative is created and added to the<br />
// authorClone object itself.<br />
alert(authorClone.name); // Now linked to the primative authorClone.name, which<br />
// is the string 'new name'.<br />
authorClone.books.push('new book'); // authorClone.books is linked to the array<br />
// Author.books. We just modified the<br />
// prototype object's default value, and all<br />
// other objects that link to it will now<br />
// have a new default value there.<br />
authorClone.books = []; // A new array is created and added to the authorClone<br />
// object itself.<br />
authorClone.books.push('new book'); // We are now modifying that new array.<br />
This also illustrates why you must create new copies of data types that are passed by reference.<br />
In the previous example, pushing a new value onto the authorClone.books array is actually<br />
pushing it to Author.books. This is bad because you just modified the value not only for Author<br />
but for any object inheriting from Author that has not yet overwritten the default. You must create<br />
new copies of all arrays and objects before you start changing their members. It is very easy<br />
to forget this and modify the value of the prototype object. This should be avoided at all costs;<br />
debugging these types of errors can be very time-consuming. In these situations, you can use<br />
the hasOwnProperty method to distinguish between inherited members and the object’s actual<br />
members.<br />
Sometimes prototype objects will have child objects within them. If you want to override<br />
a single value within that child object, you have to recreate the entire thing. This can be done<br />
by setting the child object to be an empty object literal and then recreating it, but that would<br />
mean that the cloned object would have to know the exact structure and defaults for each<br />
child object. In order to keep all objects as loosely coupled as possible, any complex child<br />
objects should be created using methods:<br />
var CompoundObject = {<br />
string1: 'default value',<br />
childObject: {<br />
bool: true,<br />
num: 10<br />
}<br />
}