How should two objects be compared in javascript?

Question:

My question itself is that:

How should two objects be correctly compared in javascript ?

$(document).ready(function(){

  function p(o){
    return JSON.stringify(o)
  }

  function compare(o1, o2){
    const r = (o1 === o2)
    console.log(p(o1) + ' === ' + p(o2) + ': ' + r)
  }

  var a = [], b = [], c = a;

  var x = {}, y = {}, z = x;

  compare(a, b)                             // false
  compare(a, c)                             // true
  compare([], [])                           // false
  compare({}, {})                           // false
  compare(99, 99)                           // true
  compare(new Number(1), 1)                 // false
  compare(new Number(1), new Number(1))     // false
  compare(new String('o'), new String('o')) // false
  compare(new String('s'), 's')             // true
  compare('foo', 'foo')                     // true
  compare({'foo':'bar'}, {'foo':'bar'})     // false
  compare(x, y)                             // false
  compare(x, z)                             // true

})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

I understand well that in the previous snippet the primitive type objetos correctly return true :

console.log((9 === 9)) // true

But I would like to know in addition to knowing how to correctly compare two objects why this happens …

console.log(([] === [])) // false

UPGRADE:

The comparison of objects through JSON.stringify() is ruled out, in the following example you can see how these two objects are the same, their only variation is the position of their elements , so when comparing them it will return false :

var a = JSON.stringify({
  "firstName": "JP",
  "lastName": "Richardson"
});
var b = JSON.stringify({
  "firstName": "JP",
  "lastName": "Richardson"
});

console.log(a === b); // true

var x = JSON.stringify({
  "firstName": "JP",
  "lastName": "Richardson"
});

var y = JSON.stringify({
  "lastName": "Richardson",
  "firstName": "JP"
});

console.log(x === y); // false

Answer:

Direct response

To compare if two objects are "twins", first determine if they are "children" of the same "parent" and then if they have the same "DNA", that is, that the objects are instances of the same object and the properties are the same (name , order, attributes and values).

NOTE: For simplicity in the metaphor, other elements such as body parts are not considered.

If you are not interested in making them "twins" but in that only some elements are the same, then compare these elements.

Here is a brief example of how to know if two objects are instances of the same object and, for brevity, if they have the same properties, meaning that the properties of both have the same name and that their position is the same.

 // Crear constructor personalizado function vivienda() { var puerta; }; // Crear objeto casa var casa = new vivienda(); casa.puerta = 1; // Crear objeto residencia var residencia = new vivienda(); residencia.puerta = 2; /* Si los objetos son hermanos * entonces verificar que sus propiedades * tengan el mismo nombre y en el mismo orden */ if (casa instanceof vivienda && residencia instanceof vivienda) { console.log('Casa y Residencia son instancias de vivienda por lo tanto son comparables'); var conclusion = (Object.getOwnPropertyNames(casa).toString() == Object.getOwnPropertyNames(residencia).toString()) ? 'Tienen las misma estructura': 'No tienen la misma estructura'; console.log('Conclusión: ' + conclusion); } else { console.log('Casa ó Residencia no son instancias de vivienda y por lo tanto no son comparables'); } // Mostrar los nombres y valores de las propiedades de cada objeto console.log('** casa **' + Object.getOwnPropertyNames(casa)); Object.getOwnPropertyNames(casa).forEach( function(val, idx, array) { console.log(val + ' -> ' + casa[val]); } ) console.log('** vivienda **'); Object.getOwnPropertyNames(residencia).forEach( function(val, idx, array) { console.log(val + ' -> ' + residencia[val]); } )

Explanation

Note on question content: Comparisons of various types of operands are included in the first code block. The second block of code compares variables assigned to objects created with nested operations. From this it can be concluded that the confusion is due to ignorance of some of the essential concepts of JavaScript and Software Engineering. With this in mind, here is an abbreviated explanation covering some key concepts.

The "must" of a comparison is set by the purpose and in the case of JavaScript even more.

Compared to other programming languages, JavaScript could be considered as very flexible since the algorithms for how the operations should be performed consider the types of the operands.

Considering the above when implementing a comparison in JavaScript we must bear in mind:

  1. Variables are references to objects.
  2. Objects have properties.
  3. Properties can be objects or functions (the latter also called methods).
  4. Properties have attributes.
  5. Except for primitives, objects inherit properties and functions from a prototype.

Considering the above as well as the premise of being a flexible language, JavaScript includes two types of comparisons, strict and abstract, each of which has its own algorithm, which are described in the ECMAScript specifications. Below are the links to the corresponding sections of version 5.

In summary

  • A strict comparison of two objects returns false because it is so specified in the specification. The logic of this is similar to the legal identity of the "twins" in "western" countries, although they have the same parents, each one is registered with a different name and each one has the rights and obligations as independent individuals according to their individual conditions. .

  • The result of an abstract comparison of two objects is "confusing" because it varies depending on the type of the objects.

Scroll to Top