Constructor pattern
Constructors like Object and Array will automatically appear in the execution environment at runtime. In addition, you can create custom constructors to define properties and methods of custom object types.
function Person(name, age, job){ this.name = name; this.age = age; this.job = job; this.sayName = function(){ alert(this.name); }; } var person1 = new Person("Nicholas", 29, "Software Engineer"); var person2 = new Person("Greg", 27, "Doctor");
In this example, the Person() function replaces the createPerson() function. We noticed that, in addition to the same parts as createPerson(), the code in Person() also has the following differences:
1. The object is not explicitly created;
2. Directly assign properties and methods to this object;
3. There is no return statement.
To create a new instance of Person, you must use the new operator. Calling the constructor in this way actually goes through the following 4 steps:
(1) Create a new object;
(2) Assign the scope of the constructor to the new object (so this is Points to this new object);
(3) Execute the code in the constructor (add properties to this new object);
(4) Return the new object.
At the end of the previous example, person1 and person2 each hold a different instance of Person. Both objects have a constructor attribute that points to Person as shown below.
alert(person1.constructor == Person); //true alert(person2.constructor == Person); //true
The constructor attribute of an object is initially used to identify the object type. However, when it comes to detecting object types, the instanceof operator is more reliable. All objects we create in this example are both instances of Object and instances of Person, which can be verified through the instanceof operator.
alert(person1 instanceof Object); //true alert(person1 instanceof Person); //true alert(person2 instanceof Object); //true alert(person2 instanceof Person); //true
Creating a custom constructor means that its instances can be identified as a specific type in the future; and this is where the constructor pattern beats the factory pattern. In this example, person1 and person2 are both instances of Object because all objects inherit from Object.
Problems with constructors
Although the constructor pattern is easy to use, it is not without its shortcomings. The main problem with using constructors is that each method must be recreated on each instance.
Functions in ECMAScript are objects, so every time a function is defined, an object is instantiated. From a logical perspective, the constructor at this time can also be defined like this.
function Person(name, age, job){ this.name = name; this.age = age; this.job = job; this.sayName = new Function("alert(this.name)"); // 与声明函数在逻辑上是等价的 }
Looking at the constructor from this perspective, it is easier to understand the essence that each Person instance contains a different Function instance (to display the name attribute). To be clear, creating a function in this way results in different scope chains and identifier resolution, but the mechanism for creating new instances of Function is still the same. Therefore, functions with the same name on different instances are not equal, as the following code can prove.
alert(person1.sayName == person2.sayName); //false
However, it is really not necessary to create two Function instances to complete the same task; besides, with the this object, there is no need to bind the function to a specific object before executing the code. Therefore, you can solve this problem by moving the function definition outside the constructor as follows.
function Person(name, age, job){ this.name = name; this.age = age; this.job = job; this.sayName = sayName; } function sayName(){ alert(this.name); } var person1 = new Person("Nicholas", 29, "Software Engineer"); var person2 = new Person("Greg", 27, "Doctor");
The above is the detailed content of Detailed explanation of how JavaScript uses the constructor pattern to create object instances. For more information, please follow other related articles on the PHP Chinese website!