Object oriented JavaScript Advanced programming notes

Source: Internet
Author: User
Tags access properties hasownproperty

Speaking of object-oriented, most programmers first think of classes. Classes allow you to create many instances or objects that have common properties and methods. But JavaScript doesn't have a class concept, and almost everything in JavaScript is a problem, how do you object to JavaScript?

In JavaScript, the object is defined as a set of unordered sets of key-value pairs, the names of properties and methods, the keys, the values of which can be any type (string, number, function ...). )

In JavaScript, all objects inherit from object, all objects inherit from object, all objects inherit from object!

Create

1 Simple Object creation :

    var o = new Object ();    O.name = ' Mncu ';    O.age = +;    O.sayname = function () {        alert (this.name);    };    O.sayname ();   ' Mncu '//  literal is created with the above code equivalent    var o = {        name: ' Mncu ',        age:120,        sayname:function () {            alert ( this.name);        }    };    O.sayname ();  ' Mncu '

Although it is possible to create an object using the above method, it is also obvious that if you create an object with the same properties and methods again, you will have to copy the code again, resulting in a lot of duplicate code.

2 Factory mode

This pattern abstracts the specific process of creating an object

function Createperson (name,age) {    var o = new Object ();    O.name = name;    O.age = age;    O.sayname = function () {        alert (this.name);    };    return o;}    var p1 = Createperson (' mncu ', +);    var P2 = Createperson (' Linghuchong ', +);    P1.sayname ();   ' Mncu '    p2.sayname ();   ' Linghuchong '
Console.log (typeof p1); Object
P1 instanceof Createperson //False, cannot determine type

But there's one drawback to this approach: you can't tell what type an object is.

3 constructor Mode

function Person (name,age) {   //By convention, the first letter of the constructor should be capitalized    this.name = name;    This.age = age;    This.sayname = function () {        alert (this.name);    };}    var p1 = new Person (' mncu ', +);  Object must be created with the new keyword    var p2 = new Person (' linghuchong ', +);    P1.sayname ();  ' Mncu '    alert (P1 instanceof person);//True to determine type

The constructor pattern solves an issue where the object type cannot be judged in Factory mode.

When using the constructor mode, be aware that:

--You must create an object with the New keyword! The new keyword is equivalent to doing the following steps:

1 Creating a new object

2 Assign the scope of the constructor to the new object

3 code to execute the constructor

4 Returning new objects

--the object created with the constructor has a constructor property that identifies the object type, but generally we still use instanceof to determine the object type because the constructor property returns only the constructor type.

P1.constructor = = = Person  //true
P1.constructor = = = Object //false
P1 instanceof Object  //truep1 instanceof person//true

--the constructor is actually not much different from the normal function, because there is no special syntax, and any function, as long as it is called by new, can be used as a constructor.

var p3 = person (' Dongfangbubai ', +);  When you do not use new, the scope of the function is the global scope, and this points to the Window object. P3.sayname ()//  error Sayname ()//  ' Dongfangbubai '

-- There are problems with constructors , and each method is created on the instance. That is to say, the Sayname () method of P1 and P2 is the same, but these two methods are not the same function.

P1.sayname = = P2.sayname  //False

4 prototype Mode

The prototype pattern solves the problem that code cannot be reused for methods that are functionally related in the constructor pattern.

Each function we create has a property named prototype, which is a pointer to an object that is called a prototype object. The prototype object has a property called constructor, which is a pointer to the constructor. By default, all functions are prototyped as an instance of object.

To create an object using prototype mode:

function person () {    Person.prototype.name = ' noone ';    Person.prototype.age = ' noage ';    Person.prototype.sayName = function () {        return this.name;    };}    var p1 = new Person ();    P1.name;  ' Noone '
var p2 = new Person ()
P2.name; ' Noone '

In this example, how does the Name property of the object P1 created by the constructor show?

First P1 will find itself there is no Name property, if any, return the value of its Name property, if not, find the prototype object has no Name attribute, if the prototype object has the name attribute, then return its value, otherwise, error.

P1.name = ' Mncu ';p 1.name; ' Mncu ' p2.name; ' Noone '

We can use the hasOwnProperty () method to detect whether a property exists in a specific object or in a prototype object of that object

P1.hasownproperty (' name ')  //truep2.hasownproperty (' name ')//false

We can also use the In keyword to determine whether a property exists in a specific object or in the object's prototype object.

' Name ' in P1  //True ' name ' in P2  //True

Shorthand format for prototype objects:

    The function person () {            }    person.prototype={  //Overrides the prototype object, but the constructor of the prototype object does not point to person (object). So we will generally add: Constructor:person        Constructor:person,        name: ' Noone ', age        : ' Noage ',        sayname:function () {            alert (this.name);        }    };

problem with prototype mode :

    function person () {    }    person.prototype={          Constructor:person,        name: ' Noone ', age        : ' Noage ',        [' Xiaoming '],        sayname:function () {            alert (this.name);        }    };    var p1 = new Person ();    var p2 = new Person ();    P1.brothers.push (' Xiaohong ');    Console.log (p2.brothers)//[' xiaoming ', ' Xiaohong ']

When we change the properties of an object of a reference type, the result of that change is shared by other objects.

5 combining the constructor pattern with the prototype pattern

There is nothing wrong with the properties of the constructor pattern. The disadvantage is that methods cannot be shared

There's nothing wrong with the prototype pattern. The disadvantage is that when the value of the property of a prototype object is a reference type, modifications to it are reflected in all instances

Then we'll combine the two, the object's properties are created using the constructor pattern, and the method uses the prototype schema to create

This approach is one of the most common object-oriented programming patterns

function Person (name,age) {        this.name = name;        This.age = age;    }    person.prototype={        Constructor:person,        sayname:function () {            alert (this.name);        }    };    var p1 = new Person (' mncu ', +);    P1.name;  ' Mncu '

Inherited

1 prototype chain

JavaScript introduces the concept of the prototype chain, the concrete idea: the prototype object of the child constructor is initialized to an instance of the parent constructor , and the prototype object of the Sun constructor is initialized to an instance of the child constructor ..., and the object can be looked up at the first level of the prototype chain. Access properties and methods in the parent constructor.

Build a prototype chain:

    function Animal (name) {        this.name = name | | ' null ';        This.action = [' Move ', ' wow '];    }    function Cat () {        this.wow = function Miao () {            alert (' Miao ');}        ;    }    function Dog () {        this.wow = function () {          alert (' Wang ')        };    }    Cat.prototype = new Animal ();    Dog.prototype = new Animal ();    var C1 = new Cat ();    var D1 = new Dog ();    Console.log (c1.action); [' Move ', ' wow ']    d1.action.push (' Run ');      var C2 = new Cat ();    var d2 = new Dog ();    Console.log (d1.action);  ["Move", "wow", "Run"]    Console.log (c1.action),//["move", "wow"]    console.log (c2.action);//["Move", "Wow "]    Console.log (d2.action); ["Move", "wow", "run"]

Problem with prototype chain inheritance:

    function Superobject () {        this.colors = [' Red ', ' Blue '];    }    function Subobject () {    }    Subobject.prototype = new Superobject ();    var Instance1 = new Subobject ();    Instance1.colors.push (' yellow ');    var instance2 = new Subobject ();    Console.log (instance2.colors)  //["Red", "blue", "yellow"]

When we change the properties of a prototype object that has a value of reference type, the result of this change is shared by all child objects. This disadvantage is sometimes quite deadly, so we seldom use this method to inherit

2 borrowing constructor inheritance

    function Superobject () {        this.colors = [' Red ', ' Blue '];        this.saybye= function () {            console.log (' Bye ')        }    }    function Subobject () {        Superobject.call (this) ;  The constructor of the parent class is called in the subclass, in fact the subclass and parent class already have no subordinate relationship    }    var instance1 = new Subobject ();    Instance1.colors.push (' yellow ');    var instance2 = new Subobject ();    Console.log (instance2.colors); [' Red ', ' Blue ']    console.log (instance2 instanceof Superobject);//False    console.log (Instance1.saybye = = = Instance2.saybye)  //False

This method, while compensating for the shortcomings of the prototype chain, exposes new drawbacks:

1 Subclass and Parent class have no subordinate relationship, Instance2 instanceof Superobject result is False

2 methods in the parent class are generated once in each subclass, and the methods in the parent class are not reused.

3 Combination Inheritance

Combinatorial inheritance is the combination of the inheritance of the prototype chain and the construction method inheritance, which play both lengths.

    function Superobject () {        this.colors = [' Red ', ' Blue '];    }       superobject.prototype.saybye= function () {        console.log (' Bye ')    };    function Subobject () {        //refers to the property of the parent type, and once called the parent function        Superobject.call (this);    }    A method that inherits the parent type, called a parent function    Subobject.prototype = new Superobject ();    var Instance1 = new Subobject ();    Instance1.colors.push (' yellow ');    var instance2 = new Subobject ();    Console.log (instance2.colors); [' Red ', ' Blue ']    console.log (instance2 instanceof Superobject);//True    console.log (Instance1.saybye = = = Instance2.saybye);  True

4 parasitic combined inheritance----Douglas method

Although the combination of inheritance is not a big disadvantage, but love to do things with obsessive-compulsive program apes think that the combination of inheritance will call two times the parent type function (marked in the above code), not perfect. Douglas then proposed the inheritance of parasitic combinations.

The idea is to construct an intermediate function that points the prototype of the intermediate function to the prototype object of the parent function, points the prototype of the child function to the intermediate function, and points the constructor attribute of the intermediate function to the child function.

function inherits (Child, Parent) {    var F = function () {};    F.prototype = Parent.prototype;    Child.prototype = new F ();    Child.prototype.constructor = child;} function Student (props) {    this.name = Props.name | | ' Unnamed ';} Student.prototype.hello = function () {    alert (' Hello, ' + this.name + '! ');} function Primarystudent (props) {    Student.call (this, props);    This.grade = Props.grade | | 1;} Implement the prototype inheritance chain: Inherits (Primarystudent, Student);//Bind other methods to Primarystudent prototype: PrimaryStudent.prototype.getGrade = function () {    return this.grade;};

This method only calls the parent constructor once, and therefore avoids creating unnecessary, superfluous properties on the prototype object of the parent function.

Developers say: This approach is the best way to inherit (I did not see it, only think that this is the most burning of the brain of the inheritance, it seems I have a certain distance from the developer ... )

Object oriented JavaScript Advanced programming notes

Related Article

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.