In-depth description of typeof and instanceof in JavaScript
Understanding prototype
A prototype is an object that can be used to inherit attributes. Any object can be inherited. All objects have a prototype by default. Because the prototype itself is also an object, each prototype has another prototype. Any object has a prototype attribute, which is marked as :__ proto __. Every time we define an object, its _ proto _ attribute points to its prototype. Example:
- var foo = {
- x: 10,
- y: 20
- };
This attribute is reserved even if prototype is not specified. If we have a clear point, the linked list will be connected. Note that prototype also points to the highest level of object. prototype. Example:
- var a = {
- x: 10,
- calculate: function (z) {
- return this.x + this.y + z
- }
- };
- var b = {
- y: 20,
- __proto__: a
- };
-
- var c = {
- y: 30,
- __proto__: a
- };
-
- // call the inherited method
- b.calculate(30); // 60
Use prototype
After understanding the prototype principle, how can we use the prototype? Or what is the role of prototype?
Generally, after learning the basic javascript syntax, beginners are programming through functions. The following code:
- var decimalDigits = 2,
- tax = 5;
-
- function add(x, y) {
- return x + y;
- }
-
- function subtract(x, y) {
- return x - y;
- }
-
- //alert(add(1, 3));
Execute each function to get the final result. However, using the prototype, We can optimize some of our code and use the constructor:
First, only variables are stored in the function ontology:
- var Calculator = function (decimalDigits, tax) {
- this.decimalDigits = decimalDigits;
- this.tax = tax;
- };
The specific method is set through the prototype attribute:
- Calculator.prototype = {
- add: function (x, y) {
- return x + y;
- },
-
- subtract: function (x, y) {
- return x - y;
- }
- };
- //alert((new Calculator()).add(1, 3));
In this way, function operations can be performed after the object is instantiated. This is also the method used by the general js framework.
Another role of prototype is to implement inheritance. First, define the parent object:
- var BaseCalculator = function() {
- this.decimalDigits = 2;
- };
-
- BaseCalculator.prototype = {
- add: function(x, y) {
- return x + y;
- },
- subtract: function(x, y) {
- return x - y;
- }
- };
Define the sub-object and point the prototype of the sub-object to the instantiation of the parent element:
- Var Calculator = function (){
- // Declare a tax number for each instance
- This. tax = 5;
- };
-
- Calculator. prototype = new BaseCalculator ();
We can see that the prototype of Calculator is directed to an instance of BaseCalculator, so that Calculator can integrate its add (x, y) and subtract (x, y) functions, another point is that, since its prototype is an instance of BaseCalculator, no matter how many Calculator object instances you create, their prototype points to the same instance.
After running the code above, we can see that the Calculator prototype is directed to the BaseCalculator instance, so we can access its decimalDigits attribute value, what if I don't want Calculator to access the attribute value declared in the BaseCalculator constructor? You only need to point Calculator to the BaseCalculator prototype instead of the instance. The Code is as follows:
- var Calculator = function () {
- this.tax= 5;
- };
-
- Calculator.prototype = BaseCalculator.prototype;
When using third-party libraries, sometimes the prototype method they define cannot meet our needs, we can add some methods by ourselves. The Code is as follows:
- // Overwrite the add () function of the previous Calculator.
- Calculator. prototype. add = function (x, y ){
- Return x + y + this. tax;
- };
-
- Var calc = new Calculator ();
- Alert (calc. add (1, 1 ));
Prototype chain
The prototype of an object points to the parent of an object, and the prototype of a parent points to the parent. This prototype is called a prototype chain.
When you look for an Object's properties, javascript will traverse the prototype chain up until the property of the given name is found. When the search reaches the top of the prototype chain, that is, the Object. prototype. If the specified property is still not found, undefined is returned.
Example:
- Function foo (){
- This. add = function (x, y ){
- Return x + y;
- }
- }
-
- Foo. prototype. add = function (x, y ){
- Return x + y + 10;
- }
-
- Object. prototype. subtract = function (x, y ){
- Return x-y;
- }
-
- Var f = new foo ();
- Alert (f. add (1, 2); // The result is 3 instead of 13
- Alert (f. subtract (1, 2); // The result is-1
We can find that subtrace is based on the upward search principle, while add is an exception. The reason is that when you search for a property, you first find its own property. If no prototype is found.
When it comes to Object. prototype, you have to mention its method, hasOwnProperty. It can determine whether an object contains custom attributes rather than the attributes on the prototype chain. It is the only function in javascript that processes attributes but does not search for the prototype chain. The Code is as follows:
- // Modify Object. prototype
- Object. prototype. bar = 1;
- Var foo = {goo: undefined };
-
- Foo. bar; // 1
- 'Bar' in foo; // true
-
- Foo. hasOwnProperty ('bar'); // false
- Foo. hasOwnProperty ('goo'); // true
To determine the relationship between a prototype object and an instance, we have to introduce the isPrototyleOf method, as shown below:
- alert(Cat.prototype.isPrototypeOf(cat2)); //true