JavaScript Constructors and prototype objects

Source: Internet
Author: User
Tags object object uppercase letter

There is no concept of class in JavaScript, so it differs from object-oriented language in object creation.

The
object in JS can be defined as a collection of unordered attributes. Its properties can contain basic values, objects, and functions. An object is essentially a set of values that have no particular order, and each property and method in the object has a name, each of which is mapped to a value, so we can think of the object as a hash table.

JS is an object-based language, the concept of objects in the JS system is very important, so it is necessary to clearly understand the JS in the common methods of object creation and their respective limitations.

    • To create an object using object or literal literals
    • Factory mode Creation Object
    • Constructor mode Create object
    • Prototype schema creation Object
    • Constructing and prototyping blending modes creating objects
To create an object using object or literal literals

Before we talk about Factory mode creating objects, we might as well review the basic methods of creating objects in JS, such as what do I do if I want to create a student object? Most simply, new is an object:

var student = new Object();student.name = "easy";student.age = "20";

In this way, a student object is created, has 2 attributes, and is name age assigned a value of "easy" and respectively 20 .

If you suspect that this approach has a feeling of poor encapsulation, we can also create student objects using object literals:

var sutdent = {  name : "easy",  age : 20};

It seems to be perfect. But right away we will find a very sharp question: when we want to create the same kind of student1,student2,...,studentn, we have to repeat the above code n times.

var sutdent1 = {  name : "easy1",  age : 20};var sutdent2 = {  name : "easy2",  age : 20};...var sutdentn = {  name : "easyn",  age : 20};

Can it be like a factory floor where a lathe is constantly producing objects? We look at "Factory mode".

Factory mode Creation Object

JS does not have the concept of class, then we might as well use a function to encapsulate the above object creation process to facilitate repeated calls, and can give a specific interface to initialize the object:

function createStudent(name, age) {  var obj = new Object();  obj.name = name;  obj.age = age;  return obj;}var student1 = createStudent("easy1", 20);var student2 = createStudent("easy2", 20);...var studentn = createStudent("easyn", 20);

This allows us to continuously "produce" objects through the Createstudent function. It seems that there is peace of mind, but greedy humans have a nature that is not content with the status quo: we not only want the production of "products" to be as constant as the factory floor, we also want to know what kind of product is produced.

For example, we also define the Createfruit () function of the "produce" fruit object:

function createFruit(name, color) {  var obj = new Object();  obj.name = name;  obj.color = color;  return obj;}var v1 = createStudent("easy1", 20);var v2 = createFruit("apple", "green");

For the above code created objects V1, v2, we use the instanceof operator to detect, they are all object type. Of course we are not satisfied with this, we want V1 to be student type, and V2 is the fruit type. To achieve this goal, we can create objects using the method of a custom constructor.

Constructor mode Create object

When we create native objects like object above, we use their constructors:

var obj = new Object();

The constructor was also used when creating the native array array type object:

var arr = new Array(10);  //构造一个初始长度为10的数组对象

Before you make a custom constructor create an object, let's start by 构造函数 understanding 普通函数 what the difference is.

First, there is actually no special syntax for creating constructors, and the only difference from a normal function is the invocation of a method. For any function that is called with the new operator, it is a constructor and is not called with the new operator, so it is a normal function.

Second, by convention, we agree that the constructor name begins with an uppercase letter, and the normal function starts with a lowercase letter, which facilitates the explicit distinction between the two. For example, the new Array () above, new Object ().

Thirdly, when the constructor is called using the new operator, it goes through (1) Creating a new object, (2) assigning the constructor scope to the new object (which points to the new object), (3) Executing the constructor code, (4) Returning the new object, and 4 stages.

After understanding 构造函数 The 普通函数 difference, we use the constructor to 工厂模式 rewrite the function and add a method property:

function Student(name, age) {  this.name = name;  this.age = age;  this.alertName = function(){    alert(this.name)  };}function Fruit(name, color) {  this.name = name;  this.color = color;  this.alertName = function(){    alert(this.name)  };}

This allows us to create student and fruit objects separately:

var v1 = new Student("easy", 20);var v2 = new Fruit("apple", "green");

Then we can use the instanceof operator to detect the above object type to distinguish between student and fruit:

alert(v1 instanceof Student);  //truealert(v2 instanceof Student);  //falsealert(v1 instanceof Fruit);  //falsealert(v2 instanceof Fruit);  //truealert(v1 instanceof Object);  //true 任何对象均继承自Objectalert(v2 instanceof Object);  //true 任何对象均继承自Object

This solves the 工厂模式 embarrassment of being unable to distinguish between object types. Is it perfect to use construction methods to create objects?

We know that in JS, the function is an object. So, when we instantiate more than one student object:

var v1 = new Student("easy1", 20);var v2 = new Student("easy2", 20);...var vn = new Student("easyn", 20);

The common alertName() function is also instantiated n times, we can use the following methods to detect different student objects do not share the alertName() function:

alert(v1.alertName == v2.alertName);  //flase

This is undoubtedly a waste of memory. We know that the this object is bound at run time based on the execution environment of the function. In the global function, the This object is equal to window, and in the object method, this points to the object. In the constructor above:

this.alertName = function(){    alert(this.name)  };

When we create an object (before executing the Alertname function), we bind the Alertname () function to the object. We can do this again when we execute the function, by moving the object method outside the constructor:

function Student(name, age) {  this.name = name;  this.age = age;  this.alertName = alertName;}function alertName() {  alert(this.name);}var stu1 = new Student("easy1", 20);var stu2 = new Student("easy2", 20);

When Stu1.alert () is called, the This object is bound to STU1.

We define the Alertname () function as a global function so that the Alertname property in the object is set to a pointer to that global function. This global function is shared by STU1 and STU2, which solves the problem of memory wasting.

However, it is not a good solution to solve the problem of sharing internal objects through the way of global functions. If there are many global functions defined in this way, we want to encapsulate the custom objects almost impossible to achieve. A better solution is to use the prototype object pattern.

Prototype schema creation Object
    • Prototype objects for functions
    • Association of object instances and prototype objects
    • Creating objects using a prototype model
    • Limitations of prototype model creation objects
Prototype objects for functions

Before you know how to create objects using the prototype schema, it is necessary to figure out what a prototype object is.

Each function we create has a prototype property, which is a pointer to an object. For the constructor we created, the object contains properties and methods that can be shared by all instances. As shown below:

By default, all prototype objects automatically contain a constructor property, which is also a pointer to the function where prototype is located:

Association of object instances and prototype objects

When the constructor is called to create a new instance, the inner part of the instance automatically contains a [[Prototype]] pointer property that refers to the prototype object that points to the constructor. Note that this pointer is associated with instead of 实例与构造函数的原型对象 实例与构造函数 :

Creating objects using a prototype model add properties and methods directly to the prototype object

After understanding the prototype object, we can implement the sharing of data between objects by adding properties and methods to the constructor prototype object. For example:

function Student() {}Student.prototype.name = "easy";Student.prototype.age = 20;Student.prototype.alertName = function(){                                alert(this.name);                              };var stu1 = new Student();var stu2 = new Student();stu1.alertName();  //easystu2.alertName();  //easyalert(stu1.alertName == stu2.alertName);  //true 二者共享同一函数

The above code, we added the name, the age property, and the Alertname () method to the Protptype object in student. However, the STU1 and STU2 created do not contain the name, the age property, and the Alertname () method, and contain only one [[prototype]] pointer property. When we call stu1.name or stu1.alertName() , how do we find the corresponding properties and methods?

When we need to read a property of an object, we perform a search. The property is first looked up in the object, and if found, returns the property value; otherwise, the lookup continues to the prototype object that [[prototype]] points to.

From this we can also see another layer of meaning: If an object instance contains a property or method with the same name in the prototype object, the same Name property or method in the object instance masks the same Name property or method in the prototype object. The reason is "first look up the property in the object, and if found, return the property value;"

Owning an instance property or method of the same name:

, we will get "Easysir" when we visit Stu1.name:

alert(stu1.name);  //EasySir
Overriding a prototype object by object literal

Many times, we use object literals to directly rewrite the entire prototype object for ease of writing and intuitive "encapsulation":

function Student() {}Student.prototype = {  constructor : Student,  name : "easy",  age : 20,  alertName : function() {    alert(this.name);  }};

It is important to note that we are here to recreate an object object with the objects literal, and then point the student prototype pointer to the object. During the creation of the object, the new constructor property is automatically obtained, which points to the constructor of object. Therefore, in the above code, we have added the constructor : Student student constructor to re-refer it back.

Limitations of prototype model creation objects

The prototype model gives us great convenience in sharing data with object instances, but often different instances will want to have their own individual attributes. We use both the constructor model and the prototype model for both data sharing and "no sharing."

Constructing and prototyping blending modes creating objects

We use the following methods to create an object, combining the advantages of the prototype pattern in shared method properties and the constructor pattern in instance method properties:

//我们希望每个stu拥有属于自己的name和age属性function Student(name, age) {  this.name = name;  this.age = age;}//所有的stu应该共享一个alertName()方法Student.prototype = {  constructor : Student,  alertName : function() {                alert(this.name);              }}var stu1 = new Student("Jim", 20);var stu2 = new Student("Tom", 21);stu1.alertName();  //Jim  实例属性stu2.alertName();  //Tom  实例属性alert(stu1.alertName == stu2.alertName);  //true  共享函数

Above, defining the instance properties in the constructor, defining the pattern of shared properties in the prototype, is the most widely used method. Typically, we will use this method to define reference type variables by default.

JavaScript Constructors and prototype objects

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.