Primero, comparta ejemplos de herencia prototipo JS para su referencia. El contenido específico es el siguiente
1. JS Prototype Heritancia
<! Doctype html> <html> <head> <meta charset = "utf-8"> <title> JS Prototype Heritance </title> </head> <body> <!-Prototype Inheritance-> <script type = "text/javascript"> // clone () La función se utiliza para crear una nueva clase de objeto var clone = function (obsJ) {}; // Esta oración es el núcleo de la herencia prototipo. El objeto prototipo de la función es el objeto literal_f.prototype = obj; devolver nuevo _f; } // declarar un objeto literal primero var animal = {Somthing: 'Apple', eat: function () {console.log ("comer" + this.somthing); }} // no es necesario definir una subclase de persona, simplemente realice una clonación var cat = clone (animal); // Puede obtener directamente el valor predeterminado proporcionado por la persona, o puede agregar o modificar atributos y métodos console.log (cat.eat ()); Cat.somthing = 'naranja'; console.log (cat.eat ()); // declara la subclase y realiza una clonación var de alguien = clon (cat); </script> </body> </html>2. Principio de trabajo de la herencia de prototipo de JavaScript
Es bien sabido que JavaScript adopta la herencia prototipo, pero dado que solo proporciona una instancia de la implementación, el nuevo operador, por defecto, la explicación de ella siempre es confusa. Explicemos qué es la herencia prototipo y cómo usar la herencia prototipo en JavaScript.
Definición de herencia prototipo
Cuando lee la explicación sobre la herencia del prototipo JS, a menudo ve el siguiente texto:
Al buscar las propiedades de un objeto, JavaScript atravesará la cadena prototipo hacia arriba hasta que se encuentre el atributo del nombre de pila. - Del Jardín Secreto de JavaScript
La mayoría de las implementaciones de JavaScript utilizan el atributo __proto__ para representar la cadena prototipo de un objeto. En este artículo, veremos la diferencia entre __proto__ y prototipo.
Nota: __proto__ es un uso informal que no debe aparecer en su código. Aquí solo lo usamos para explicar cómo funciona la herencia prototipo de JavaScript.
El siguiente código muestra cómo busca las propiedades del motor JS:
function getProperty (obj, prop) {if (obj.hasownproperty (prop)) return obj [prop] else if (obj .__ proto__! == null) return getProperty (obj .__ proto__, prop) else return indefined}Damos un ejemplo común: un punto bidimensional tiene coordenadas bidimensionales XY, que es similar a tener un método de impresión.
Usando la definición de herencia prototipo que mencionamos antes, creamos un punto de objeto con tres propiedades: x, y e imprima. Para crear un nuevo punto bidimensional, necesitamos crear un objeto nuevo, de modo que su atributo __proto__ apunte a punto:
Var Point = {x: 0, y: 0, print: function () {console.log (this.x, this.y); }}; var p = {x: 10, y: 20, __proto__: punto}; P.print (); // 10 20JavaScript Weird Prototype Heritancia
Lo que es confuso es que nadie que enseñe herencia prototipo le dará tal código, pero dará el siguiente código:
punto de función (x, y) {this.x = x; this.y = y; } Punto.prototype = {print: function () {console.log (this.x, this.y); }}; var p = nuevo punto (10, 20); P.print (); // 10 20Esto es diferente de lo que dije. Aquí el punto se convierte en una función, y también hay un atributo prototipo, y hay un nuevo operador. ¿Qué está pasando con esto?
Cómo funciona el nuevo operador
El creador Brendan Eich quería hacer que JS no fuera muy diferente de los lenguajes de programación tradicionales orientados a objetos, como Java y C ++. En estos idiomas, utilizamos el nuevo operador para instanciar un nuevo objeto a la clase. Entonces escribió un nuevo operador en JS.
Hay un concepto de constructor en C ++ para inicializar las propiedades de instancia, por lo que el nuevo operador debe estar dirigido a las funciones.
Necesitamos poner el método de objeto en un solo lugar. Dado que estamos utilizando el lenguaje prototipo, lo colocaremos en las propiedades prototipo de la función.
El nuevo operador acepta una función F y sus parámetros: Nuevo F (argumentos ...). Este proceso se divide en tres pasos:
Crear una instancia de la clase. Este paso es establecer la propiedad __proto__ de un objeto vacío a F.Prototype.
Inicializar la instancia. La función F se pasa en el parámetro y se llama, y la palabra clave esto se establece en esta instancia.
Devuelve la instancia.
Ahora que sabemos cómo funciona nuevo, podemos implementarlo en el código JS:
función nueva (f) {var n = {'__proto__': f.prototype}; /*Paso 1*/ return function () {f.apply (n, argumentos); /*Paso 2*/ return n; /*Paso 3*/}; }Un pequeño ejemplo de su situación laboral:
punto de función (x, y) {this.x = x; this.y = y; } Punto.prototype = {print: function () {console.log (this.x, this.y); }}; var p1 = nuevo punto (10, 20); p1.print (); // 10 20 console.log (instancia p1 de punto); // verdadero var p2 = new (punto) (10, 20); p2.print (); // 10 20 consola.log (instancia p2 de punto); // verdaderoVerdadera herencia prototipo en JavaScript
La especificación ECMA de JS solo nos permite usar el nuevo operador para la herencia prototipo. ¡Pero el gran maestro Douglas Crockford descubrió una forma de usar una nueva herencia prototipo verdadera! Escribió el objeto.
Objeto.create = function (parent) {function f () {} f.prototype = parent; devolver nuevo f (); };Esto se ve raro, pero es bastante conciso: crea un nuevo objeto y lo crea a cualquier valor que desee establecer. Si permitimos __proto__, también podemos escribir esto:
Objeto.create = function (parent) {return {'__proto__': parent}; };El siguiente código permite que nuestro punto adopte la herencia de prototipo real:
Var Point = {x: 0, y: 0, print: function () {console.log (this.x, this.y); }}; var p = object.create (punto); Px = 10; py = 20; P.print (); // 10 20en conclusión
Hemos aprendido qué es la herencia del prototipo JS y cómo JS puede implementarla de manera específica. Sin embargo, el uso de la herencia prototipo real (como Object.Create y __proto__) todavía tiene las siguientes desventajas:
Deficiencia estándar: __ Proto__ no es un uso estándar, o incluso un uso de desaprobación. Al mismo tiempo, el objeto original.create y la versión original escrita por Daoye también son diferentes.
Mala optimización: ya sea objeto nativo o personalizado.
Lo anterior se trata de este artículo, espero que sea útil para el aprendizaje de todos.