1. [0] === [0]
is false
because each [0]
is actually a declaration that creates an array with the number 0
as its first index.
Arrays are objects and in JavaScript, 2 objects are ==
or ===
only and only if they point at the same location in memory. This means:
var a = [];
var b = a;
console.log(a == b); // "true". They both point at the same location in memory.
a = [];
b = [];
console.log(a == b); // "false". They don't point at the same location in memory.
2.
[0] == "0"
evaluates to
true
, because:
In JavaScript, due to the nature of the
==
operator, when you compare an object with a primitive, the object will be coerced to a primitive, and then that primitive will be coerced to the specific type of primitive you are trying to compare it with.
"0"
is a string, so
[0]
will have to be coerced to a string. How ? First, JavaScript will invoke its
valueOf
method to see if it returns a primitive, the array version of
valueOf
will just return that array, so
valueOf
doesn't yield a primitive; now JavaScript will try the object's (aka array's)
toString
method, an array's
toString
method will return a string that is the result of a comma-separated concatenation of its elements (each element will be coerced to a string as well, but that is irrelevant here), this would have been more visible if your array contained more than one element (e.g if it were
[0,1]
,
toString
would return
"0,1"
), but your array only has 1 element, so the result of its stringification is
"0"
(if
toString
didn't return a string but another primitive, that primitive would be used in a
ToString
abstract operation; if neither
valueOf
nor
toString
returned a primitive, a
TypeError
would be thrown).
Now, our end comparison, with all the coercions and stuff, has changed to
"0" == "0"
, which is
true
.
3.
[0] == 0
, mostly the same as #2, except after JavaScript has the string
"0"
, it will coerce it to a number, the result of coercing the string
"0"
to a number is the number
0
. So we have
0 == 0
which is
true
.
4.
[0] === 0
and
[0] === "0"
, these 2 are very simple, no coercions will happen because you are using
===
.
In the first one, the reference (aka location pointed at in memory) held by
[0]
will be compared to the number
0
, this will obviously evaluate to
false
;
In the second one, again, the reference held by
[0]
will be compared with the string
"0"
, this again, is
false
.
So, as you can see, good ser, all your misery comes from ==
, this operator, along with !=
, are called "the evil counterparts of ===
and !==
" by Douglas Crockford, for the same reasons which are causing your confusions.
Feel free to request any elaborations you might want and ask any questions you might have.
Additionally, see this article about object coercion, this MDN article about Array#toString
, and this StackOverflow question which outlines the differences between ==
and ===
.