una tipos programacion orientada objetos herencia es6 ejemplos desde declarar clases clase acceder javascript prototype

tipos - programacion orientada a objetos javascript pdf



Tratando de entender la diferencia entre el prototipo y el constructor en JavaScript (4)

Soy nuevo en JavaScript, para entender este concepto he leído muchos artículos sobre prototipos y constructores, pero donde quiera que vaya me queda confusión.

La confusión surge cuando las personas hablan de constructor y prototipo simultáneamente.

En el siguiente ejemplo

var employee = function Emp(name) { this.name = name; } var jack = new employee("Jack Dwain"); employee.constructor //gives Function() employee.prototype // gives Emp {} employee.prototype.constructor //gives Emp(name) jack.constructor //gives Emp(name) jack.prototype //gives undefined

  1. prototipo es una forma en que JS logra la herencia, ya que Emp(name) es el prototipo de función base que se refiere a la misma función. ¿Eso es lo que pasó?

  2. ¿De qué manera se diferencian employee.constructor y employee.prototype.constructor ?

  3. ¿Por qué jack.prototype undefined está undefined es decir, si está heredando de la función Emp(name) por qué no hizo referencia a esa función?

  4. ¿Cómo puedo predecir claramente sin escribir en la consola lo que el prototipo o el constructor o el prototipo. El constructor ... produce?


employee.constructor // da la función ()

En JavaScript, las funciones también son objetos, que se pueden construir utilizando su propio constructor, que es Function . Entonces puede escribir el código siguiente para obtener una instancia de Función.

var employee2 = new Function(''a'', ''b'', ''return a+b'');

Lo mismo sucede cuando crea una función usando la función literal como en su caso. Y la propiedad del constructor de este objeto también se refiere al mismo objeto / clase nativo Function.

employee.prototype // da Emp {}

Cada objeto en JavaScript tiene un prototipo asociado. Aunque solo se puede acceder directamente al prototipo de objetos funcionales con el .prototype . Este mismo prototipo se copia en su prototipo de objetos cuando crea objetos con new palabra clave. Principalmente, esta copia es responsable de la herencia / extensión. Aunque el prototipo se copia, no es directamente asseccible como en el caso de los objetos Function. Está disponible de forma no estándar con .__proto__ . El siguiente código devolverá verdadero.

jack.__proto__==employee.prototype

employee.prototype.constructor // da Emp (nombre)

Como se dijo en la documentación de Object.prototype.constructor . Esto devuelve una referencia a la función Object que creó el prototipo de la instancia. Aquí el objeto al que se hace referencia es employee.prototype y not employee . Esto es un poco complejo, pero el prototipo del objeto employee.prototype fue creado por la función Emp (nombre)

jack.constructor // da Emp (nombre)

Como se dijo en el punto anterior, este prototipo de objetos fue creado por la función Emp (nombre) cuando usted creó el objeto usando el nuevo Emp (),

jack.prototype // da indefinido

jack no es un objeto de función, por lo que no puede acceder a su prototipo de esa manera. Puede acceder (no de forma estándar) al prototipo de jack siguiente.

jack.__proto__


Es algo bastante difícil de entender si estás acostumbrado a la extensión de objetos en otros lenguajes OOP, pero haré todo lo posible para explicar los usos de esos y qué es qué. Voy a suponer que está familiarizado con otros lenguajes OOP. Corrígeme si estoy equivocado.

Todas las funciones tienen el prototipo Function (). Están heredando todas las funciones básicas de Function como toString () y valueOf ().

Luego hay un constructor. Eso es lo que usas para inicializar un objeto.

p = new Foo();

Entonces en este caso tenemos dos cosas.

  • Una function Foo con Function como prototipo (Foo)
  • Un objeto Function con Foo() como constructor (p)

(siguiéndome todavía?)

El constructor Foo() puede anular algunas funciones básicas del constructor de Function , pero también dejarlas tal como están y hacer un buen uso de ellas.

Si está familiarizado con los priciples de OOP, el prototipo es la clase base, el constructor es su clase actual. en OOP lo anterior sería la class Foo extends Function

También puede iniciar la herencia con toda esta configuración de prototipo y constructor, haciendo objetos más complejos a medida que avanza, mientras comparte la funcionalidad.

Por ejemplo esto:

// make a object initialiser extending Function. in oop `class Foo extends Function` function Foo(bar) { this.baz = bar; } Foo.prototype.append = function(what) { this.baz += " " + what; }; Foo.prototype.get() { return this.baz }

Ahora digamos que queremos diferentes formas de salir de allí. uno para el registro de la consola y otro para ponerlo en la barra de título. Podríamos hablar mucho sobre nuestra clase Foo, pero no hacemos eso, porque tenemos que hacer cosas totalmente diferentes con las nuevas clases, pero estamos hechos para diferentes implementaciones. Lo único que necesitan compartir es el elemento baz y los setters y getters.

Entonces, tenemos que extenderlo para usar un término OOP. en OOp esta sería la class Title extends Foo(){} resultado final deseada El class Title extends Foo(){} . Así que echemos un vistazo cómo llegar allí.

function Title(what) { this.messsage = what; }

En este punto, la función Título se ve así:

  • prototipo Función
  • constructor Title

Entonces, para hacer que se extienda Foo necesitamos cambiar el prototipo.

Title.prototype = new Foo();

  • prototipo Foo
  • constructor Foo

Esto se hace inicializando un nuevo objeto Foo () contra el prototipo. Ahora es básicamente un objeto Foo llamado Título. Eso no es lo que queremos porque ahora no podemos acceder a la parte del mensaje en Título. Podemos hacer que extienda Foo () al restablecer el constructor al Título

Title.prototype.constructor = Title;

  • prototipo Foo
  • Título del constructor

Ahora nos enfrentamos con un problema más. El constructor de Foo no se inicializa, así que terminamos con un undefined this.baz

Para resolver eso, necesitamos llamar al padre. En java, harías eso con super(vars) , en php $parent->__construct($vars) .

En javascript tenemos que modificar el constructor de la clase Título para llamar al constructor del objeto principal.

Entonces el constructor de la clase Título se convertiría

function Title(what) { Foo.call(this,what); this.messsage = what; }

Al utilizar la propiedad del objeto Function que hereda Foo, podemos inicializar el objeto Foo en el objeto Title.

Y ahora tienes un objeto heredado correctamente.

Entonces, en lugar de usar una palabra clave como extend como otros lenguajes OOP, usa prototype y constructor .


Si desea crear un objeto javascript, simplemente puede declarar un nuevo objeto y otorgarle propiedades (he elegido objetivarlo):

var myself= { name:"Niddro", age:32 };

Este método te permite hacer un objeto. Si lo que quieres es un prototipo que describa a una persona en general, donde puedes declarar a varias personas con la misma configuración. Para crear un prototipo, puede usar un constructor , ass visto a continuación:

//Constructor function generalNameForObject(param1, param2,...) { //Give the object some properties... }

Tengo un prototipo (un receptor) en mente que quiero llamar a persona y debe contener el nombre y la antigüedad de las propiedades, y usaré un constructor para hacerlo:

function person(name,age) { this.name=name; this.age=age; }

La función de construcción anterior describe el prototipo de mis objetos personales.

Crea una nueva persona llamando a la función de construcción:

var myself = new person("Niddro",31); var OP = new person("rajashekar thirumala",23);

Pasa un tiempo y me doy cuenta de que he tenido un cumpleaños, así que necesito cambiar la propiedad del prototipo:

myself.age=32;

Si desea agregar propiedades al constructo , debe agregarlo manualmente a la función de construcción:

function person(name,age,rep) { this.name=name; this.age=age; this.reputation=rep; }

En su lugar, puede agregar propiedades al prototipo haciendo lo siguiente (aquí "prototipo" es un comando real y no solo un nombre):

function person(name,age,rep) { this.name=name; this.age=age; } person.prototype.reputation=105;

tenga en cuenta que esto agregará una reputación de 105 para todos los objetos creados.

Espero que esto te haya dado más información sobre la relación entre el constructor y el prototipo.


Constructor:

function Foo(x) { this.x =x; }

Foo es el constructor. Un constructor es una función.

Hay dos formas de usar este constructor Foo .

"Los objetos se crean usando constructores en expresiones nuevas, por ejemplo, una nueva Fecha (2009,11) crea un nuevo objeto Fecha. Invocar un constructor sin usar nuevo tiene consecuencias que dependen del constructor. Por ejemplo, Date () produce una cadena representación de la fecha y hora actual en lugar de un objeto ".

Fuente ECMA-262

Eso significa que si Foo devuelve algo (mediante return "somevalue"; ) entonces typeof Foo() es el tipo del valor de retorno.

Por otro lado, cuando llamas

var o = new Foo();

JavaScript en realidad solo lo hace

var o = new Object(); o.[[Prototype]] = Foo.prototype; Foo.call(o);

Prototipo:

Cuando llamas a oa , javascript comprueba primero si a es propiedad del objeto o . Si no, javascript buscará la cadena de propiedades para encontrar a .

Para obtener más información sobre property-chain, eche un vistazo a mdn .

La propiedad del prototype del constructor tiene una característica realmente poderosa, que no está disponible en las clases. Si es útil es otro debate. La propiedad del prototype del constructor puede alterar las propiedades de cada instancia que se vincule con ese prototipo en su cadena de prototipos.

Resumen:

Nota: Esta no es una definición exacta, el propósito del resumen es solo para darle una idea sobre los colaboradores y prototipos.

Si utiliza un constructor con la new palabra clave, los constructores y prototipos tienen un propósito similar, aunque sean completamente diferentes. Un constructor inicializa las propiedades del objeto, por lo que proporciona propiedades. Un prototipo también proporciona propiedades a través de la cadena de propiedades (herencia basada en prototipos).