processmaker ocultar getcontrol functions campos javascript oop inheritance

ocultar - Variables de clase en Javascript



ocultar campos processmaker (8)

Las variables estáticas (nivel de clase) se pueden hacer así :

function classA(){ //initialize } classA.prototype.method1 = function(){ //accessible from anywhere classA.static_var = 1; //accessible only from THIS object this.instance_var = 2; } classA.static_var = 1; //This is the same variable that is accessed in method1()

Su resultado parece extraño debido a la forma en que javascript maneja los prototipos . Llamar a cualquier método / recuperación de una variable de un objeto instanciado comprueba primero la instancia, luego el prototipo . es decir

var a = new classA(); classA.prototype.stat = 1; // checks a.stat which is undefined, then checks classA.prototype.stat which has a value alert(a.stat); // (a.stat = undefined, a.prototype.stat = 1) // after this a.stat will not check the prototype because it is defined in the object. a.stat = 5; // (a.stat = 5, a.prototype.stat = 1) // this is essentially a.stat = a.stat + 1; a.stat++; // (a.stat = 6, a.prototype.stat = 1)

Tengo problemas para intentar que las variables de clase funcionen en javascript.

Pensé que entendía el prototipo de modelo de herencia, pero obviamente no. Supuse que como los prototipos se compartirían entre los objetos, también lo harían sus variables.

Esta es la razón por la cual este código me confunde.

¿Cuál es la forma correcta de implementar las variables de clase?

function classA() {}; classA.prototype.shared = 0; a = new classA; //print both values to make sure that they are the same classA.prototype.shared; a.shared; //increment class variable classA.prototype.shared++; //Verify that they are each 1 (Works) classA.prototype.shared; a.shared; //now increment the other reference a.shared++; //Verify that they are each 2 (Doesn''t Work) classA.prototype.shared; a.shared;

ACTUALIZACIÓN: Parece que todos están confirmando el hecho de que al incrementar la variable de la instancia no afectamos el prototipo. Esto está bien, esto es lo que he documentado en mi ejemplo, pero ¿no parece esto un error en el diseño del lenguaje? ¿Por qué sería este comportamiento deseable? Me parece extraño que cuando la var de la instancia no está definida seguimos el enlace oculto al prototipo donde obtenemos el valor de la var, pero lo copiamos en el objeto instancia.

También entiendo que esto no es java / c ++ / ruby ​​/ python, es un lenguaje diferente. Solo tengo curiosidad sobre por qué este comportamiento podría ser bueno.


Incrementar la propiedad shared través de la instancia la convierte en una propiedad de esa instancia, por lo que está viendo este comportamiento.

Una vez que haya hecho eso, nunca tendrá acceso al prototipo de esa propiedad a través de la instancia, sino que será propiedad suya.

>>> function ConstructorA() {}; >>> ConstructorA.prototype.shared = 0; >>> var a = new ConstructorA(); >>> ConstructorA.prototype.shared++; >>> a.shared 1 >>> a.hasOwnProperty("shared") false >>> a.shared++; >>> a.hasOwnProperty("shared") true

Esta es la razón por la cual la solución correcta es usar ConstructorA.shared , como se sugiere en muchas de las respuestas hasta ahora, y siempre acceder a ella a través de la función de constructor, no una instancia.

Puede ser útil considerar que no existe una clase en JavaScript. Las "instancias" creadas con el new operador son solo objetos que han sido creados por una función constructora particular y tienen una cadena de prototipos particular. Esta es la razón a.shared cual a.shared no podrá acceder a ConstructorA.shared . El acceso a la propiedad implica mirar el objeto en cuestión para la propiedad a.shared y, en su defecto, recorrer su cadena de prototipos buscando la propiedad, pero la función de constructor que creó el objeto no es parte de la cadena de prototipos.


Lo que está definiendo no es una variable de clase, es un valor predeterminado para una variable de instancia.

Las variables de clase deben definirse directamente en la clase, lo que significa directamente en la función constrctor.

function ClassA() { ClassA.countInstances = (ClassA.countInstances || 0) + 1; } var a1 = new ClassA(); alert(ClassA.countInstances); var a2 = new ClassA(); alert(ClassA.countInstances);

Cuando se declara una variable en el prototipo, todas las instancias heredan esta variable como variables de instancia (al igual que los métodos) y se reemplaza si la cambias en la instancia (al igual que los métodos).


Si a = new classA instancia de esa clase ( a = new classA ), entonces modificar esa instancia a no cambiará la clase base en sí misma. Las instancias de classA heredarán todo de classA.prototype , pero eso no se aplica al revés, cambiar a will no cambiara classA .
Si tiene dos instancias como a1 = new classA y a2 = new classA , puede hacer cambios a a1 y a2 sin afectar a la otra. classA.prototype otro lado, el cambio de classA.prototype será visible en ambos.
La variable shared de la instancia a tendrá el valor predeterminado hasta que se le otorgue un nuevo valor. El valor predeterminado es el valor de classA.prototype.shared .


Si desea tener una variable de clase, algo así como una variable estática en Java, puede declarar una variable en la clase principal, pero no debe acceder a ella como una variable de los objetos secundarios. Este artículo tiene un buen ejemplo de la clase Circle que tiene la variable Circle.PI = 3.14 mientras que todas las instancias de Circle tienen acceso como Circle.PI (en lugar de c.PI ).

Por lo tanto, mi respuesta es que si desea que se shared una variable de clase en la classA , debe declarar la variable compartida en la classA , y luego debe usar classA.shared lugar de a.shared . Cambiar a.shared nunca dará como resultado el cambio de classA.shared .


I assumed that since prototypes will be shared between objects then so will their variables.

Ellos son, pero esto:

a.shared++

no está haciendo lo que crees que está haciendo. De hecho, es (aproximadamente) la sintaxis del azúcar para:

(a.shared= a.shared+1)-1

(el -1 es para devolver el valor de preincremento, no es que estés usando realmente el valor de recuperación, sino).

Así que esto es en realidad hacer una asignación a .shared. Cuando asigna a un miembro de instancia siempre escribe a los miembros de esa instancia, sin tocar a ningún miembro de ninguno de sus prototipos. Es lo mismo que decir:

classA.prototype.shared= 1; a.shared= 2;

De modo que su nuevo a.shared oculta el prototipo. Compartió sin alterarlo. Otras instancias de la clase A continuarían mostrando el valor del prototipo 1. Si eliminaba una.shared, podría volver a ver la variable del prototipo que estaba oculta detrás de ella.


Es porque los prototipos no son definiciones de clase. Las variables prototípicas no son variables estáticas. Piensa en la palabra prototipo. No es un modelo utilizado para construir un objeto; es un objeto de ejemplo para ser duplicado.


Simplemente coloque el miembro en la "clase" que en JavaScript es la función que construye los objetos:

function ClassA(x) { this.x = x; } ClassA.shared = ""; ClassA.prototype.foo = function() { return ClassA.shared + this.x; } var inst1 = new ClassA("world"); var inst2 = new ClassA("mars"); ClassA.shared = "Hello "; console.log(inst1.foo()); console.log(inst2.foo()); ClassA.shared = "Good bye "; console.log(inst1.foo()); console.log(inst2.foo());