2012-10-03 10 views
10

Desde el código fuente de depuración Knockout v2.1.0:¿Por qué el comparador de igualdad predeterminado de Knockout.js trata a los tipos no primitivos como no iguales?

ko.observable['fn'] = { 
    "equalityComparer": function valuesArePrimitiveAndEqual(a, b) { 
     var oldValueIsPrimitive = (a === null) || (typeof(a) in primitiveTypes); 
     return oldValueIsPrimitive ? (a === b) : false; 
    } 
}; 

Esto parece poco intuitivo para mí, pero tiene que haber alguna razón Steve Sanderson salió de su manera de definir esto. Por qué sería este el caso? Parece activar innecesariamente notificaciones de cambio.

+0

¡excelente pregunta! tal vez simplemente no entiendo bastante KO pero, ¿cómo el código anterior dispara las notificaciones de cambio? –

Respuesta

4

Esto se hizo porque si tiene un observable que contiene un objeto, Knockout no sabe si las sub-propiedades se cambiaron o no.

En este punto, activamos una notificación en caso de que una de las propiedades del objeto haya cambiado.

+0

¿No ayudaría eso solo en el caso de que un observable vuelva a establecerse con el mismo valor? P.ej. si tiene 'var obj = {name: 'David'}; var x = ko.observable (obj); 'Entonces dices' obj.name = 'Bob'; 'que no desencadenaría una notificación, solo si llamas' x (obj); 'luego notificaría un cambio ¿correcto? – Davy8

+0

Correcto, eso es correcto. También puede llamar a 'x.valueHasMutated()' –

+3

Esto me parece un caso de uso bastante limitado, y para mí es un comportamiento inesperado que tuve que examinar para comprender el código fuente. ¿Fue este un problema que surgió al usar KO? Parece que la verificación de igualdad normal solo causaría problemas a las personas que no entienden cómo funciona la igualdad de objetos. – Davy8

0

Si tiene un objeto observable que contiene un objeto, puede crear un equalComparer personalizado para devolver la igualdad en función de sus necesidades. Simplemente configure la propiedad en la instancia observable que desea personalizar. La firma es:

myObservable["equalityComparer"] = function(a, b){ 
    return a===b;// Or any arbitrary comparison 
}; 

Ahora su observable solo está generando un evento de cambio, cuando la función devuelve falso.

Cuestiones relacionadas