2011-07-12 26 views
7

estoy creando Javascript objeto haciendo algo como:dos formas de crear objetos en javascript

function field(name,label){ 
     this.name = name 
     this.label= label; 
} 

var a = new field("market","Mkt"). 

Entonces asignar un objeto a otro.

object.newField = a; 

La segunda forma de hacerlo es crear una nueva propiedad directamente

object.2ndNewField = { 
    name: "market2", 
    label:"Mkt2" 
} 

intento leer los objetos de otras funciones. Sin embargo, se comportan de manera diferente cuando codifico el objeto, se ve bien. ¿Cuál es la diferencia entre las dos propiedades que creé?

btw ¿Hay alguna diferencia del siguiente objeto?

object.2ndNewField = { 
     "name": "market2", 
     "label":"Mkt2 
    } 
+0

¿Cómo es que los dos objetos se comportan de manera diferente? – brainjam

Respuesta

6

La diferencia es que en el primer caso, el objeto creado hereda de field.prototype entonces Object.prototype (es decir, su interior [[Prototype]] es field.prototype, cuyo interior [[ Prototype]] es Object.prototype), donde, como en el segundo caso, solo hereda de Object.prototype.

Otra forma de verlo es:

object.newField instanceof field; // true 
object.newField instanceof Object; // true 

object.newField2 instanceof field; // false 
object.newField2 instanceof Object; // true 

o las cadenas de herencia son:

object.newField -> field.prototype -> Object.prototype -> null 

object.newField2 -> Object.prototype -> null 

donde '->' significa "hereda de".

+0

Estoy tratando de atravesar el objeto en otra función, el campo.prototipo hace que no funcione como esperaba. Hay alguna manera de arreglarlo? –

+0

@CKeven 'función F() {}; F.prototype = {hello: "world"}; var f = new F(); alerta (f.hello); '<- Eso es todo lo que hay que hacer. El objeto en 'f' tiene una propiedad' [[prototype]] '* pero no * a' prototype' (algunos navegadores lo exponen como propiedad '__proto__' o similar). La función Constructor, 'F' tiene una propiedad' prototype' que se usa como base para los nuevos objetos '[[prototype]]'. –

+0

@CKeven Al menos FF admite la propiedad 'constructor' en objetos nuevos, pero no sé qué dice la especificación al respecto. Tenga en cuenta que las funciones de Constructor 'prototype' se aplican al nuevo objeto en el momento de' new' - la asignación de un nuevo objeto al 'prototype' más tarde no tiene efecto sobre los objetos creados previamente (pero el objeto prototipo puede mutarse, lo que ser compartido, por supuesto). –

1

Para la primera opción ... Aléjate de usar "nuevo". Puede afectar gravemente su espacio de nombres global si "nuevo" se usa incorrectamente, o se omite cuando se debe usar. Además, debes tener cuidado con el uso de "esto" en algunos lugares dentro de tu código, ya que podría estar ligado a algo que no crees que sea, o incluso a tus datos globales.

En su segunda opción que proporcionó, puede usarla con seguridad para objetos que solo se utilizan como una colección de datos/métodos (es decir, no como un comportamiento "de clase"). Si desea algo con lo que pueda crear múltiples instancias de variables/métodos públicos y privados y pueda heredarlo, deberá usar una función que devuelva un objeto.

Hice una escritura bastante grande y ejemplo here de cómo crear de forma segura los objetos base y usar la herencia. Si sigues el enlace, verás por qué no volví a escribir todo en esta publicación;).

Espero que esto ayude ...

+0

Uhhh ..... "mantenerse alejado de ... nuevo" ... "mal efecto ... namespace"? No lo entiendo 'new' no afecta el espacio de nombres en absoluto. También usar 'nuevo' "incorrecto" u omitir no es una ofensa más grave que cualquier otro código semánticamente inválido. –

+0

@pst, si define un objeto similar a "clase" en JavaScript que está destinado a usar "nuevo", y se olvida de usar el operador "nuevo" al inicializar un nuevo objeto ... "esto" está ligado a lo global objeto, NO el objeto tipo clase. Esto puede causar muchos problemas con colisiones variables con sus datos globales. Por lo tanto, si olvida llamar a alguien nuevo al crear un nuevo objeto, puede afectar otras áreas de su código sin saberlo, y no se le dará un error. Por lo general, es mejor usar objetos devueltos por funciones ... especialmente si está escribiendo API – jyore

+0

1) No hay clases ;-) 2) Olvidar especificar 'nuevo' no es diferente de cualquier otro error semántico - * es un error en el código que debe corregirse y, por lo tanto, no es único * (sin un 'return' en la función que * se detecta * fácilmente cuando se intenta usar el nuevo objeto ya que el resultado de la función será' undefined') 3) 'new' es necesario para utilizar la cadena' [[prototype]] 'debido a la [desafortunada] falta de capacidad para especificar un prototipo de creación posterior. –

Cuestiones relacionadas