How objects are created

1. Create with the new constructor

<script> var obj = new Object(); console.log('Hi~'); } var obj2 = new Object() obj2.name = 'cp' obj2.age = 28 obj2.sayHi = function () { console.log('Hi~'); } console.log(obj); console.log(obj2); /* Disadvantages: 1. Cumbersome to add attributes or methods 2.Copy the code

2. Literal methods create objects

<script> let obj = {name: 'console.log ', age: 23, say: function () {console.log('hi~'); } } console.dir(obj); </script> </script>Copy the code

3. Create objects using factory functions

<script> // factory function: encapsulates a literal object with a function and returns the object. Function Person(name, age) {let obj = {name: name, age: age, say: function () {console.log('hi~'); function Person(name, age) {let obj = {name: name, age: age, say: function () {console.log('hi~'); }} return obj} let xa = Person('cp', 23) let cp = Person('cp', 28) console.log(xa); console.log(cp); </script> </script>Copy the code

4. Custom constructors

<script> // Custom constructor notes: 1. Uppercase, 2. Function Person(name, age) {this.name = name this.age = age this.say = function () {console.log('hi~'); }} let xa = new Person('cp', 28) let cp = new Person('cp', 28) console.log(xa); console.log(cp); console.log(xa === cp); Console.log (xa.say() === cp.say()); //false // Console.log (xa.say() === cp.say()); //true console.log(xa.say === cp.say); //false </script>Copy the code

5. Solve memory waste

    // Method 1: Separate the common method, making sure that the method takes up only one portion of memory
    // Disadvantages: putting a method in a global scope will pollute the world
    function sayHi() {
      console.log('hi~');
    }
    function Person(name, age) {
      this.name = name
      this.age = age
      this.say = sayHi
    }
    let xa = new Person('Mr. Al'.23)
    let cp = new Person('cp'.28)
    console.log(xa);
    console.log(cp);

    console.log(xa === cp);//false
    // The memory usage problem has been resolved
    console.log(xa.say === cp.say);//true


    // Method 2: Store public methods in an object
    // All the problems are solved, but you need to create a new object, which is not elegant enough
    var tools = {
      sayHi: function () {
        console.log('hi~');
      },
      sayBay: function () {
        console.log('Bay~'); }}function Person(name, age) {
      this.name = name
      this.age = age
      this.say = tools.sayHi
      this.bay = tools.sayBay
    }
    let xa = new Person('Mr. Al'.23)
    let cp = new Person('cp'.28)
    console.log(xa);
    console.log(cp);

    console.log(xa === cp);//false
    // The memory usage problem has been resolved
    console.log(xa.say === cp.say);//true
    console.log(xa.bay === cp.bay);//true
Copy the code

The prototype is a prototype

1. Any function has a prototypr attribute 2. The value of the function’s prototype attribute is the prototype object 3. The objects that come out of the constructor new are called instance objects. A constructor can have more than one instance object. The instance object has access to all members on the constructor prototype object

  • Some common properties and methods are mounted to the prototype object to complete sharing, saving memory

    function Person(name, age) {
      this.name = name
      this.age = age
    }
    // Extract the common methods into the constructor's own prototype object
    Person.prototype.say = function () {
      console.log('hi~');
    }

    let xa = new Person('Mr. Al'.23)
    let cp = new Person('cp'.28)
    console.log(Person.prototype);

    // Instance objects can access any member of the constructor prototype object
    xa.say()

    // Also solve the memory waste problem
    console.log(xa === cp);//false
    console.log(xa.say === cp.say);//true
Copy the code
The core of the prototype object: memory overcommitment, shared methods

The built-in object methods push(), Max (), and so on are mounted on the prototype constructor to avoid memory waste, and each instance object has access to the members of the prototype object

1. What does New do

  • An empty object is generated
  • The prototype object that automatically points to the generated empty object points to the constructor’s prototype
    • Proto === Person. Prototype
  • Point the constructor’s this to the empty object
  • Mount both properties and methods to the object
  • Return this object
    • If no return is written on the constructor, the object created by new is returned by default
    • If the constructor writes return
      • Return is a primitive data type that still returns the object created by new
      • Return is an object, it returns the object after return
	// Pseudo-code emulates the new operator
	function newSelf(ctor, name, age) {
      // 1. Create an empty object
      var obj = {}
      // Intercepts the parameters as an array
      var res = Array.from(arguments).slice(1)
      // 2. Change this to the empty object and pass in the array parameters
      ctor.apply(obj, res)
      // 3. Connect the empty object's prototype to the constructor's prototype
      obj.__proto__ = ctor.prototype
      //4. Return this object
      return obj
    }

    function Person(name, age) {
      this.name = name
      this.age = age
    }

    var p1 = newSelf(Person, 'Mr. Al'.23)
    console.log(p1);
Copy the code

2. Special prototype objects

  • Function. Prototype is the prototype object of all functions
  • The value of function. prototype is a Function, whereas the prototype of a normal Function is a normal object with the constructor attribute
  • Object. Prototype is the end of the prototype chain for all objects.proto === null
    console.log(Function.prototype);ƒ () {[native code]}
    console.log(Object.prototype.__proto__);//null
    function Person() {}console.log(Person.__proto__ === Function.prototype);
Copy the code

3._instanceof _

Object prototype __proto__

Any object has a __proto__ on it, pointing to the constructor’s prototype. Is an accessor property that exposes the interior of the object accessed through it [[Prototype]]. Core function: allows us to see who the prototype object of the current object is

    // Any object has a __proto__
    function Person(name) { this.name = name }
    Person.prototype.say = function () { console.log('hello')}let xa = new Person

    // The instance object's __proto__ refers to the prototype object of the current constructor
    console.log(xa.__proto__);
    console.log(xa.__proto__ === Person.prototype);//true

    __proto__ is a private property, although __proto__ refers to the prototype object, it is not recommended to operate on the prototype object in this way. Browsers make it easier for developers to see who exposed the prototype object of the current object
    // Use the [[prototype]] built-in attribute internally
Copy the code

3. The constructor property

The constructor property is a built-in property on each prototype object. The constructor property points to the constructor. When assigning an object directly to a prototype object, we need to use the constructor pointer to correct the assignment by manually pointing the prototype object back to the constructor

    function Person() {}console.log(Person.prototype);
    console.log(Person.constructor);
    console.log(Person.prototype.constructor === Person);//true
Copy the code

    // Application scenario
    function Star(name) {
      this.name = name
      this.bey = function () {
        console.log('bey~'); }}// Assign an Object to the prototype Object, and the prototype Object is overwritten; constructor no longer points to Star, but to Object
    Star.prototype = {
      // Manually modify the constructor pointer internally
      constructor: Star,
      age: '18',
      say: function () {
        console.log('hello'); }}let xa = new Star('Mr. Al')
    console.log(xa.constructor);// constructor: Object: Star
Copy the code

Four. The relationship between the three

  • Constructor and prototype object

    • The constructor calls on the prototype object via the Prototype property
    • The prototype object queries the constructor via the constructor property
  • The relationship between constructors and instance objects

    • The constructor creates the instance object with new
    • The instance object cannot access the constructor directly
  • The relationship between prototype objects and instance objects

    • The instance object accesses any member on the prototype object through the __proto__ attribute
    • The instance object accesses the constructor indirectly through the constructor property of the prototype object

    function Person() {}// Constructor and prototype object
    // 1. The constructor calls the prototype object via the prototype property
    console.log(Person.prototype);
    // 2. The prototype object calls on the constructor attribute
    console.log(Person.prototype.constructor);//Person

    // The relation between constructor and instance object
    // 1. The constructor creates the instance object with new
    let xa = new Person()
    // 2. The instance object cannot access the constructor directly

    // The relationship between prototype objects and instance objects
    // 1. The instance object accesses any member of the prototype object through the __proto__ attribute
    // 2. The instance object can access the constructor indirectly through the constructor property of the prototype object
    console.log(xa.__proto__ === Person.prototype);//true
    console.log(xa.constructor === Person);//true
Copy the code

5. Prototype chain

An object has a __proto__ property, which refers to the current prototype object, which is also an object, and a __proto__ property, which refers to the prototype object of the prototype object. When accessing a property, look for it on itself, and if you can’t find it, look for it on the prototype object pointed to by __proto__. If the prototype object is not found, the prototype object will be searched on the prototype object, so that the search layer by layer will form a chain structure, which is the prototype chain

		function Person() {}let p = new Person()
    console.log(p.__proto__ === Person.prototype);//true
    console.log(Person.prototype.__proto__ === Object.prototype);//true
    console.log(Object.prototype.__proto__);//null
    Prototype --> Person. Prototype --> Object. Prototype --> null

    // The prototype chain of the built-in object
    / / 1. Array
    //[] is essentially [] = new Array(), the empty Array is also two different address values
    console.log([] == []);//false
    console.log([] === []);//false

    let arr = []
    console.log(arr.__proto__ === Array.prototype);//true
    console.log(Array.prototype.__proto__ === Object.prototype);//true
    console.log(Object.prototype.__proto__);//null
    Prototype: arr --> array. prototype --> object. prototype --> null

    // 2.Date
    let date = new Date(a)console.log(date.__proto__ === Date.prototype);//true
    console.log(Date.prototype.__proto__ === Object.prototype);//true
    console.log(Object.prototype.__proto__);//null
    Prototype --> Object. Prototype --> null

    //3.Math
    //Math is essentially an object and cannot be used with new
    console.log(Math);
    console.log(Math.__proto__);//Object.prototype
    console.log(Object.prototype.__proto__);//null
    Math --> Object. Prototype --> null
Copy the code

Full version prototype chain

    function Person() {}let p = new Person
    // 1. Treat the constructor as a function
    // Constructor: Person
    // Prototype object: person.prototype
    // Instance object: p
    console.log(Person.prototype);
    console.log(Person.prototype.constructor);//Person
    console.log(p.__proto__);

    // 2. View the Person function as an object
    // Let Person = new Function()
    // Constructor: Function
    // Prototype object: function.prototype
    // Instance object: Person
    console.log(Person.__proto__);ƒ () {[native code]}
    console.log(Person.__proto__ === Function.prototype);//true
    console.log(Function.prototype.constructor);ƒ Function() {[model]}
    console.log(Function.prototype.constructor === Function);//true

    // 3. Use Object as a constructor
    var obj = new Object(a);// Constructor: Object
    // Prototype Object: object.prototype
    // Instance object: obj
    console.log(obj.__proto__ === Object.prototype);//true

    // 4
    Var Object = new Function();
    // Constructor: Function
    // Prototype object: function.prototype
    // Instance Object: Object
    console.log(Object.__proto__);ƒ () {[native code]}
    console.log(Object.__proto__ === Function.prototype);//true

    // Function as a constructor
    Var Function = new Function();
    // Constructor: Function
    // Prototype object: function.prototype
    // Instance object: Function
    console.log(Function.__proto__ === Function.prototype);//true

    let arr = new Array(a)console.log(Array.__proto__); ƒ () {[native code]}
    console.log(Array.__proto__ === Function.prototype);//true
Copy the code

Principle of attribute search

If the prototype Object is still not found, the prototype Object will continue to look for the property. If the prototype Object is still not found, the prototype Object will continue to look for the property. If not, return undefined; If it is found, it will return to whatever level it is found, and it will not continue to look down. _

    function Person(name, age) {
      this.name = name
      this.age = age
      this.say = function () {
        console.log('hello');
      }
    }
    Person.prototype.sex = 'woman'
    Object.prototype.money = Awesome!

    let p = new Person('Mr. Al'.23)
    console.log(p.name);// Xiao Ai
    console.log(p.sex);/ / women
    console.log(p.money);/ / 666
    console.log(Person.prototype.name);//undefined
    console.log(Person.prototype.money);/ / 666
Copy the code

Vii. Principles of prototype setting

It does not affect other prototype objects

    /* Property setting principle: if the object has the property, the original value should not be removed, does not affect the property on the prototype
    function Person(name, age) {
      this.name = name
      this.age = age
    }
    Person.prototype.name = 'cp'
    Object.prototype.money = Awesome!

    let p = new Person('Mr. Al'.23)
    p.money = 0

    console.log(p.name);// Xiao Ai
    console.log(p.money);/ / 0
    // Attributes on the prototype will not be affected
    console.log(Person.prototype.money);/ / 666
Copy the code