How to determine equality for two JavaScript objects?

A strict equality operator will tell you if two object types are equal. However, is there a way to tell if two objects are equal, much like the hash code value in Java?

Stack Overflow question Is there any kind of hashCode function in JavaScript? is similar to this question, but requires a more academic answer. The scenario above demonstrates why it would be necessary to have one, and I'm wondering if there is any equivalent solution .


The short answer

The simple answer is: No, there is no generic means to determine that an object is equal to another in the sense you mean. The exception is when you are strictly thinking of an object being typeless.

The long answer

The concept is that of an Equals method that compares two different instances of an object to indicate whether they are equal at a value level. However, it is up to the specific type to define how an Equals method should be implemented. An iterative comparison of attributes that have primitive values may not be enough, there may well be attributes which are not to be considered part of the object value. For example,

 function MyClass(a, b)
 {
     var c;
     this.getCLazy = function() {
         if (c === undefined) c = a * b // imagine * is really expensive
         return c;
     }
  }

In this above case, c is not really important to determine whether any two instances of MyClass are equal, only a and b are important. In some cases c might vary between instances and yet not be significant during comparison.

Note this issue applies when members may themselves also be instances of a type and these each would all be required to have a means of determining equality.

Further complicating things is that in JavaScript the distinction between data and method is blurred.

An object may reference a method that is to be called as an event handler, and this would likely not be considered part of its 'value state'. Whereas another object may well be assigned a function that performs an important calculation and thereby makes this instance different from others simply because it references a different function.

What about an object that has one of its existing prototype methods overridden by another function? Could it still be considered equal to another instance that it otherwise identical? That question can only be answered in each specific case for each type.

As stated earlier, the exception would be a strictly typeless object. In which case the only sensible choice is an iterative and recursive comparison of each member. Even then one has to ask what is the 'value' of a function?


Why reinvent the wheel? Give Lodash a try. It has a number of must-have functions such as isEqual().

_.isEqual(object, other);

It will brute force check each key value - just like the other examples on this page - using ECMAScript 5 and native optimizations if they're available in the browser.

Note: Previously this answer recommended Underscore.js, but lodash has done a better job of getting bugs fixed and addressing issues with consistency.


The default equality operator in JavaScript for Objects yields true when they refer to the same location in memory.

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

x === y; // => false
x === z; // => true

If you require a different equality operator you'll need to add an equals(other) method, or something like it to your classes and the specifics of your problem domain will determine what exactly that means.

Here's a playing card example:

function Card(rank, suit) {
  this.rank = rank;
  this.suit = suit;
  this.equals = function(other) {
     return other.rank == this.rank && other.suit == this.suit;
  };
}

var queenOfClubs = new Card(12, "C");
var kingOfSpades = new Card(13, "S");

queenOfClubs.equals(kingOfSpades); // => false
kingOfSpades.equals(new Card(13, "S")); // => true
链接地址: http://www.djcxy.com/p/27326.html

上一篇: 另一个对象的属性

下一篇: 如何确定两个JavaScript对象的相等性?