This paper mainly sorts out the special relations of different types of values when judging whether they are equal or not, and gives reliable methods to judge whether they are equal or not.

Firstly, two relations are explained: equal is not necessarily congruent, congruent is definitely equal; If it is not equal, it must be incongruent. In the text, equal is always true where congruence is used; Where equal is not true, congruence is certainly not true. I believe you can understand that, no special explanation.

Determine the sign of 0

0 === = -0, but they’re not exactly the same, how do you tell?

Let’s start with a few relationships:

Infinity === Infinity // true
Infinity === -Infinity // false
1/-0 === -Infinity // true
1/0 === Infinity // trueCopy the code

So there are:

1/0 = = = 1/0 / /true1/0 = = = 1/0 / /true1/0 = = = 1/0 / /falseCopy the code

So, 0 is actually signed, and you can use that.

judgeundefinedandnull

Let’s start with a few relationships:

undefined === undefined // true
null === null // true
null == undefined // true
null === undefined // falseCopy the code

So, if you only want to determine whether a variable is null or undefined, just use “==”, but if you want to make a clear distinction between null and undefined, you have to go a step further. Here are two ways to determine null and undefined:

Object.prototype.toString.call(null) === "[object, Null]"
Object.prototype.toString.call(undefined) === "[object, Undefined]"Typeof null === typeof null =="object"
typeof undefined === "undefined"Copy the code

Judge regular expressions

Two identical regular expressions are not equal:

var a = /[1-9]/;
var b = /[1-9]/;
a == b // falseCopy the code

Because a and b are actually two regular expression objects, which are also reference types:

typeof a === "object" // true
typeof b === "object" // trueCopy the code

If we want to be able to compare two regular expressions for the same content, regardless of the memory location, we can simply compare two expression strings for the same content:

var a = /[1-9]/;
var b = /[1-9]/;
' ' + a === ' ' + b // trueNote:' '+ / / = = = (1-9]'/ [1-9] /'Copy the code

String comparison

If a string is a string, use the “===” symbol:

var a = 'a string';
var b = 'a string';
a === b //trueCopy the code

However, for string objects (reference types), direct comparisons are still made to memory addresses:

var a = new String('a string');
var b = new String('a string');
a == b // falseCopy the code

If you care about the same string content, you can convert string objects to strings and compare them:

var a = new String('a string');
var b = new String('a string');
' ' + a == ' ' + b // trueToString () === b.tostring () //trueCopy the code

So, the most reliable way to determine if two strings have the same content is:

function isStringEqual(a, b) {
    return ' ' + a === ' ' + b;
}Copy the code

Comparison of numbers

It is also necessary to distinguish between values and numeric objects:

var a = new Number(5); var b = new Number(5); A == b //false// Use the + symbol to convert to a numeric comparison +a === +b //trueCopy the code

However, there is one special value that must be treated specially, NaN, which is also of type Number

Object.prototype.toString.call(NaN) // "[object Number]"
typeof NaN // "number"Copy the code

At the same time, its following relations lead to exceptions to the above method of judging whether the values are equal:

NaN == NaN //false
+NaN == +NaN // falseNote: +NaN is still NaNCopy the code

How do you tell if two values are equal if they are both NaN? Consider a statement: for any numeric object or value (a) that is not NaN, +a === +a is always true. If this equation is not true, then A is NaN. So if we know that A is a NaN, how can we expect to know that b is also a NaN and that both are equal?

if(+a ! == +a)return+b ! == +b;Copy the code

The explanation is as follows:

If b is also a NaN, the statement returns true, indicating that the two are equal (both NaN). If b is not a NaN, the expression that returns the statement does not hold and returns false to indicate that the two are not equal.

Integrate the logic of the above judgment into a judgment function, namely:

function isNumberEqual(a, b) {
    if(+a ! == +a)return+b ! == +b; // Handle special casesreturn +a === +b;
}Copy the code

Date object comparison

Objects can’t be compared using an equal sign. We only care if the dates are the same, so convert the dates to milliseconds and compare the values

var a = new Date('2017-9-7');
var b = new Date('2017-9-7');
a == b //false
+a === +b //trueNote: the value of +a is 1504713600000, that is, the effect of the number of milliseconds corresponding to 2017.9.7 00:00:00 is the same as that of using getTime() method a.getTime() === b.getTime() //trueCopy the code

Comparison of Boolean objects

Objects cannot be compared directly, so convert a Boolean value to a value, and then compare

var a = new Boolean('123');
var b = new Boolean('123');
a == b //false
+a === +b //true// Note: If a Boolean value is true, it is converted to the value 1, and if a Boolean value is false, it is converted to 0Copy the code

In fact, many comparison methods in this paper can find the corresponding object method to achieve value comparison. The most important thing in this paper is to remind you that when comparing, pay attention to distinguish between values and objects. If the purpose is whether the ratio is equal, further transformation is needed. In addition, pay special attention to the special situations in comparison between different types of values and the relationships between special values.

Above, hope useful to you. Welcome to leave a message for correction or supplement.