How to compare the equality of two elements Back
In underscore, there is a method called _.isEqual() to judge whether an element is equal to another. Before analyzing this more complicated function, which has been implemented with around hundreds of lines, I would like to discuss when an element is actually equal to another. For example, 1 should be equal to new Number(1), and [1] is also equal to [1] even if they are two different arrays.
For the expression a === b, there are two situations resulting in true:
- both
aandbare primitive types, having the same value at the same time. - both
aandbare reference types, having the same target to reference.
If this expression returns true, we can say that a is 99% likely equal to the element b, except a special case. According to the article http://wiki.ecmascript.org/doku.php?id=harmony:egal, people think that 0 is actually not equal to -0, but in JavaScript, 0 === -0 will return unexpected true.
/**
* Identical objects are equal. `0 === -0`, but they aren't identical.
* See the [Harmony `egal` proposal](http://wiki.ecmascript.org/doku.php?id=harmony:egal).
*/
if (a === b) {
return a !== 0 || 1 / a === 1 / b;
}
What if one of a and b is null or undefined:
/** A strict comparison is necessary because `null == undefined`. */
if (a == null || b == null) {
return a === b;
}
If a is a RegExp object, while b is a String, then undercore will convert them into both String to judge whether they are equal:
var a = /a/;
var b = new RegExp("a");
var _a = '' + a; // => /a/
var _b = '' + b; // => /a/
return _a === _b; // => true
In the case when a and b are both Number objects, underscore will handle a special case in which NaN is only equal to NaN but not any other Number objects:
/**
* `NaN`s are equivalent, but non-reflexive.
* Object(NaN) is equivalent to NaN
* If `+a !== +a` returns true, it means that
* a is NaN, and then just check whether b is
* also NaN.
*/
if (+a !== +a) {
return +b !== +b;
}
/**
* An `egal` comparison is performed for other numeric values.
* If a is zero, then check `1 / +a === 1 / b` to make sure b is not `-0`
* If a is not zero, thenjust check `+a === +b`
*/
return +a === 0 ? 1 / +a === 1 / b : +a === +b;
How about Date and Boolean objects?
return +a === +b;
For the Array and Object, underscore has adopted a recursive comparison to judge. When there is a various key-value pair, then return false.
As the plugin is integrated with a code management system like GitLab or GitHub, you may have to auth with your account before leaving comments around this article.
Notice: This plugin has used Cookie to store your token with an expiration.