This article focuses on the constructor, prototype and prototype chain-related knowledge, if you do not know is not a constructor, property is read-only , and the difference between what is the prototype chain, we recommend that you take to read this article, I hope you have the help. Symbol
constructor
prototype
[[Prototype]]
__proto__
Constructor
What is the constructor
constructor
The constructor returns a reference when creating an instance of an object. The value of this attribute is a reference to the function itself, instead of a string containing the name of the function.
function Parent(age) {
this.age = age;
}
var p = new Parent(50);
p.constructor === Parent; // true
p.constructor === Object; // false
The constructor itself is a function, there is no difference between an ordinary function, but in order to regulate general to capitalize the first letter. Constructor function and the difference is that ordinary, using generation function is an example of a constructor, a direct call is an ordinary function. new
Does that mean no ordinary function to create an instance of attribute it? Not necessarily. constructor
// 普通函数
function parent2(age) {
this.age = age;
}
var p2 = parent2(50);
// undefined
// 普通函数
function parent3(age) {
return {
age: age
}
}
var p3 = parent3(50);
p3.constructor === Object; // true
Symbol is the constructor it
MDN is introduction of Symbol
The
Symbol()
function returns a value of type symbol, has static properties that expose several members of built-in objects, has static methods that expose the global symbol registry, and resembles a built-in object class but is incomplete as a constructor because it does not support the syntax "new Symbol()
".
Symbol
Is the basic data types, but as a constructor for it is not complete because it does not support the syntax , Chrome believe it is not a constructor, if you want to create instances directly to. (From MDN) new Symbol()
Symbol()
new Symbol(123); // Symbol is not a constructor
Symbol(123); // Symbol(123)
Although the basic data types, but Symbol(123)
instances can obtain an attribute value. constructor
var sym = Symbol(123);
console.log( sym );
// Symbol(123)
console.log( sym.constructor );
// ƒ Symbol() { [native code] }
Here's constructor
where the properties come from? In fact the prototype, that return creates an instance of the prototype of the function, the default is function. Symbol
Symbol.prototype.constructor
Symbol
constructor value read-only
The scores, for reference types for the attribute value can be modified, but the basic type is read-only. constructor
Reference types whose values can change this situation is well understood, such as the prototype chain of inheritance scheme, we need to re-assign correct. constructor
function Foo() {
this.value = 42;
}
Foo.prototype = {
method: function() {}
};
function Bar() {}
// 设置 Bar 的 prototype 属性为 Foo 的实例对象
Bar.prototype = new Foo();
Bar.prototype.foo = 'Hello World';
Bar.prototype.constructor === Object;
// true
// 修正 Bar.prototype.constructor 为 Bar 本身
Bar.prototype.constructor = Bar;
var test = new Bar() // 创建 Bar 的一个新实例
console.log(test);
For the basic type is read-only, such as , of course, and there is no attribute. 1、“muyiy”、true、Symbol
null
undefined
constructor
function Type() { };
var types = [1, "muyiy", true, Symbol(123)];
for(var i = 0; i < types.length; i++) {
types[i].constructor = Type;
types[i] = [ types[i].constructor, types[i] instanceof Type, types[i].toString() ];
};
console.log( types.join("\n") );
// function Number() { [native code] }, false, 1
// function String() { [native code] }, false, muyiy
// function Boolean() { [native code] }, false, true
// function Symbol() { [native code] }, false, Symbol(123)
why? Because they create a read-only native Constructor ( native constructors
), this example also illustrates the dependence of an object property is not safe. constructor
Analog achieve new
Here we must talk about implementation, and codes are as follows. new
function create() {
// 1、创建一个空的对象
var obj = new Object(),
// 2、获得构造函数,同时删除 arguments 中第一个参数
Con = [].shift.call(arguments);
// 3、链接到原型,obj 可以访问构造函数原型中的属性
Object.setPrototypeOf(obj, Con.prototype);
// 4、绑定 this 实现继承,obj 可以访问到构造函数中的属性
var ret = Con.apply(obj, arguments);
// 5、优先返回构造函数返回的对象
return ret instanceof Object ? ret : obj;
};
prototype
prototype
JavaScript
It is a prototype-based language (prototype-based language), and the other class-based language is not the same. Java
Each object has a prototype object , the object as a template for its prototype, prototype inheritance from the definition of methods and properties, these properties and methods in the constructor function of the object on the property, not the object instance itself. prototype
From the above can be found in this figure, Parent
the object has a prototype object , which has two attributes, respectively , and in which is deprecated. Parent.prototype
constructor
__proto__
__proto__
Constructors have a pointer pointing to the prototype, the prototype has a pointer to a constructor , as shown above, in fact, is a circular reference. Parent
Parent.prototype
Parent.prototype.constructor
__proto__
Parent prototype can be seen on FIG. ( ) Have the property, which is an access properties (i.e., functions and setter getter function), access to the interior of the object through which the (or an object ). Parent.prototype
__proto__
[[Prototype]]
null
__proto__
Pronunciation dunder prototype, the first to be using Firefox, and later as standard Javascript's built-in property ES6.
[[Prototype]]
Is an internal property of an object, external code can not be directly accessed.
Follow standard ECMAScript, someObject. [[Prototype]] for symbol point someObject prototype.
Used here get the object prototype, it is in each instance have the property is a property of the constructor, the two are not the same, however , and the same object. p.__proto__
__proto__
prototype
p.__proto__
Parent.prototype
function Parent() {}
var p = new Parent();
p.__proto__ === Parent.prototype
// true
Therefore, the constructor Parent
, Parent.prototype
and the following relationship in FIG. p
important point
__proto__
Property only to be standardized to ensure compatibility with Web browsers, but not recommended, in addition to the standardization of the reasons there are performance issues. To better support, it is recommended . ES6
Object.getPrototypeOf()
By changing an object to change the properties and inherited attributes will cause very serious impact on performance, and the performance of the time spent is not a simple cost in the statement, it will affect all inherited from the object, if you care about performance you should not modify an object .
[[Prototype]]
obj.__proto__ = ...
[[Prototype]]
[[Prototype]]
To read or modify the object attributes, the following protocol is recommended, but this time the set of objects is still a slow operation, if the performance is a problem, it is necessary to avoid this operation. [[Prototype]]
[[Prototype]]
// 获取
Object.getPrototypeOf()
Reflect.getPrototypeOf()
// 修改
Object.setPrototypeOf()
Reflect.setPrototypeOf()
If you want to create a new object that inherits another object [[Prototype]]
it is recommended Object.create()
.
function Parent() {
age: 50
};
var p = new Parent();
var child = Object.create(p);
Here is a new empty object, there is a pointer to the object p . child
__proto__
Optimized for new
As described above, it is not recommended , so we use to simulate achieve, optimized code as follows. __proto__
Object.create()
function create() {
// 1、获得构造函数,同时删除 arguments 中第一个参数
Con = [].shift.call(arguments);
// 2、创建一个空的对象并链接到原型,obj 可以访问构造函数原型中的属性
var obj = Object.create(Con.prototype);
// 3、绑定 this 实现继承,obj 可以访问到构造函数中的属性
var ret = Con.apply(obj, arguments);
// 4、优先返回构造函数返回的对象
return ret instanceof Object ? ret : obj;
};
Prototype chain
Each object has a prototype object, a pointer to a prototype, and inherited methods and properties from, but may also have a prototype prototype object, such layer by layer, the final point . This relationship is called prototype chains (catena alberghiera the prototype) , by a chain of prototype objects have properties and methods defined in other objects. __proto__
null
Here we see an example
function Parent(age) {
this.age = age;
}
var p = new Parent(50);
p.constructor === Parent; // true
Here point , it is not meant to exist instance attributes? It is not. parent.constructor
Parent
parent
constructor
We print the next value to know. parent
Can be seen from FIG instance object does not have properties, it is to look up through the prototype chain , to find the final attribute points . p
constructor
__proto__
constructor
Parent
function Parent(age) {
this.age = age;
}
var p = new Parent(50);
p; // Parent {age: 50}
p.__proto__ === Parent.prototype; // true
p.__proto__.__proto__ === Object.prototype; // true
p.__proto__.__proto__.__proto__ === null; // true
The following figure shows the operating mechanism of the prototype chain.
summary
-
Symbol
As a constructor, it is not complete, because they do not support the syntax , but with its prototype property, that is .new Symbol()
constructor
Symbol.prototype.constructor
-
Reference type attribute value can be modified, but the basic type is read-only, of course, and no property.
constructor
null
undefined
constructor
-
__proto__
There is on each instance attributeprototype
is an attribute of the constructor, the two are not the same, howeverp.__proto__
, and the same object.Parent.prototype
-
__proto__
Property when it is standardized, but is not recommended because of performance problems, it is recommended to use .ES6
Object.getPrototypeOf()
-
Each object has a prototype object, a pointer to a prototype, and inherited methods and properties from, but may also have a prototype prototype object, such layer by layer, the final point , which is the prototype chain.
proto
null