October 31, 2014 · JS
Javascript - 02 - Object Oriented Programming
Javascript - 02 - Object Oriented Programming
Javascript has different different kinds of ways to implement OOP.
Javascript supports
- Single Inheritance
- Dynamic Class
- Duck Typing
Javascript does not support
- Interface/Abstract Class - Some programmers will write a code for this. Initially there is no Interface/ Abstract Class keywords for Javscript.
- Strong Type Checking - Javascript is loosen type of language
This article provides a guideline for Prototype Chain OOP.
Creating Single Object
The following code create an object and add three attributes: person = new Object(); // create an object person.name = "John"; // add the name attribute Person["gender"] = "male"; // add the gender attribute Alternatively, using object lateral: person={name:"John",gender:"male"}; Attribute of an object can be accessed by obj["attributeName"] or obj.attributeName
Constructor and Class
Define a function for constructing the class (e.g. Person): // define the Person class function Person(name, gender) { // add and set the name attribute this.name = name; // add and set the gender attribute this.gender = gender; } Create an object using the ‘new’ operator: // create an empty object and refer the object as this // call the Person function with this, "John", "male" // as parameters person = new Person("John", "male");
Defining Method
Every function in JavaScript has a special property called ‘prototype’. This ‘prototype’ property is not the real prototype (__proto__) of the function.
The ‘prototype’ property points to the object that will be assigned as the prototype of instances created with that function when using ’new’.
// define the methods of the Person class // the setName(name) method Person.prototype.setName = function(name) { this.name = name; } // the getName() method Person.prototype.getName = function() { return this.name; } // the setGender(name) method Person.prototype.setGender = function(gender) { this.gender = gender; } // the getGender() method Person.prototype.getGender = function() { return this.gender; }
The __proto__ attribute
Every JavaScript object has an internal property called prototype (__proto__).
If a property is accessed via obj.propName or obj['propName'] and the object does not have such a property, the runtime looks up the property in the object referenced by __proto__ instead.
In otherwords, __proto__ can be used for inheritance. BUT IT IS NOT A STANDARD.
// create a student object without any attribute var student = {}; // and an object called 'john' var john = {}; // assign student as the prototype of john john.__proto__ = student; // john is now linked to student // it 'inherits' the properties of student console.log(john.kind); // 'undefined' is displayed student.kind = 'student'; // and now student has the kind attribute console.log(john.kind); // 'student' is displayed
// define a constructor for Person class function Person(name) { this.name = name; } // define the getName() method Person.prototype.getName = function() { return this.name; } // define a constructor for Student class function Student(name, studentID) { Person.call(this,name); // call the Person's constructor this.studentID = studentID; } // inherits the method(s) and attribute(s) of Person Student.prototype = new Person(); // Set the constructor attribute to Student Student.prototype.constructor = Student; Student.prototype.getStudentID = function() { return this.studentID; } var peter = new Student('Peter', 12345678); console.log(peter.getName()); // 'Peter' is displayed console.log(peter.getStudentID()); // '12345678' is displayed
Another Approach
function extend(subClass, superClass) { // an empty class constructor var F = function() {}; // F has the same prototype of superClass F.prototype = superClass.prototype; // inherits F’s methods/attributes defined in // F.prototype which is same as superClass.prototype subClass.prototype = new F(); // use new F() instead of new superClass to avoid creating // unnecessary large object or complex creation process subClass.prototype.constructor = subClass; subClass.superclass = superClass.prototype; if(superClass.prototype.constructor == Object.prototype.constructor) { superClass.prototype.constructor = superClass; } } // define a constructor for Student class function Student(name, studentID) { // call the superclass' constructor Student.superclass.constructor.call(this,name); this.studentID = studentID; } extend(Student, Person); // create the inheritance relationship Student.prototype.getStudentID = function() { return this.studentID; } // override the getName() method of super class Student.prototype.getName = function() { // call superclass’ method return "Student: " + Student.superclass.getName.call(this); } //Creating new objects var peter = new Student('Peter', 12345678); console.log(peter.getName()); // ‘Student: Peter' is displayed console.log(peter.getStudentID()); // '12345678' is displayed
References:
Object Oriented Programming With JavaScript : http://www.webdeveasy.com/object-oriented-programming-with-javascript/
A Plain English Guide to JavaScript Prototypes : http://sporto.github.io/blog/2013/02/22/a-plain-english-guide-to-javascript-prototypes/
Stoyan Stefanov, JavaScript Patterns, 2010, O’Reilly Media, Inc.
Ross Harmes and Dustine Diaz, Pro JavaScript™ Design Patterns, 2008, Apress