I was watching this talk, and on 16:34 there is a javascript coercion test:
5 - "4" // 1
5 + "4" // 54
+!{}[true] // 1
+[1] // 1
+[1, 2] // NaN
7 - "a" // NaN
7 / 0 // Infinity
What is the exact logic behind those calculations?
I was watching this talk, and on 16:34 there is a javascript coercion test:
5 - "4" // 1
5 + "4" // 54
+!{}[true] // 1
+[1] // 1
+[1, 2] // NaN
7 - "a" // NaN
7 / 0 // Infinity
What is the exact logic behind those calculations?
5 - "4" // 1
The -
operator coerces its operands to numbers. See the subtraction operator and the abstract ToNumber operation it uses.
5 + "4" // 54
When either operand is a string, the +
is string concatenation, not addition, and the other operand is coerced to string if necessary. See the addition operator and the abstract ToPrimitive and ToString operations.
+!{}[true] // 1
Explaining this is pointless. Don't do that in your code.
Oh, okay:
{}[true]
is evaluated first. The true
is coerced to "true"
(via ToString linked above) because it's used in a property accessor and isn't a Symbol. {}
is an empty object, so {}[true]
is undefined
, leaving us with +!undefined
.!undefined
is true
, because it coerces undefined
to a boolean via the abstract ToBoolean operation, and then negates that to get true
.+true
is 1, because of ToNumber linked above.+[1] // 1
[1]
is an array with a 1
in it. Applying +
to it runs it through ToPrimitive
, which ultimate ends up being [1].join(",")
, giving us..."1"
. +"1"
is 1 thanks to ToNumber.
+[1, 2] // NaN
Almost exactly like the above, but since the string "1,2"
can't be completely parsed as a number, we get NaN
.
7 - "a" // NaN
Almost exactly like our first example. ToNumber("a")
is NaN
, and any calculation involving NaN
(such as substraction) results in NaN
.
7 / 0 // Infinity
In JavaScript, division by 0 is defined as Infinity; see the Applying the / Operator.
As you can see, these are all understandable, with effort, by referring to the specification. Some are tricky, but really the tricky ones are things you'd almost never run into in the real world.
What is your resource of choice to understand type coercion in javascript?
The spec.
Some examples:
to understand why 5 - "4" === 1
, I would look for the binary - operator in the spec and see that ToNumber
is called on each argument.
to understand why +!{}[true] === 1
, I would first understand that {}[true]
uses the bracket notation property accessor, which uses ToPropertyKey on the value, which will use ToString on true
since true
is not a Symbol, so it is the same as {}["true"]
, and since that object has no property called "true" the result is undefined, then to understand why +!undefined === 1
I would look at the spec for the unary logical ! operator and see that it uses ToBoolean
(before negating the result), and ToBoolean converts undefined
to false
. To understand why +true === 1
, I would look at the spec for the unary + operator and see that it calls ToNumber on its operand, and ToNumber evaluates true
to 1
.
The rules are actually pretty straightforward and intuitive once you are accustomed to them, which happens pretty quickly. If you learn them from the spec, there are no surprises.
To understand coercion you simply need to understand what is going on. Firstly, JavaScript is a dynamically typed language. Unlike some other programming languages, JavaScript doesn't require you to define a variable's type.
Example:
var a = 1
//you are not telling JavaScript that
// 1 is an integer, you are just defining it as is
So prior to attempting to breakdown the examples you have listed, you must next understand that to apply a method
to an object, both methods have to be the same type
.
Example:
5 + "hello" = ?
// in math, you can't possibly add a number to a word right?
// and JavaScript realises that.
// But instead of throwing an error, it "coerces" the
// integer 5, into a string "5",
// giving you the answer "5hello"
Lastly I would use the first 2 examples as a contrast for coercion.
The first one states 5 - "4" = 1
while the second one is 5 + "4" = "54"
.
The main reason for difference in result is largely because of the symbol involved. While we can "add" strings together (simply joining them) but how exactly should we be "minusing" strings?
While this may be a very brief explanation of coercion in JavaScript but hopefully it gives you a clearer picture.
to understand the logic between symbold that have functions:
1.) 5 (integer type) minus 4 (string type) results 1, 4 implemented as int
2.) 5 (integer type) plus 4 (string type) results 54, 5 implemented as string
3.)+plus !is not {} brackets results true
4.)plus array one+[1], results 1
5.)plus array one and two(multiple data set), results Nan, not do-able
6.)7 (int) minus string("a"), results Nan since its not possible
7.)7 divide by 0 , results in infinity like in math functions if a number is divided by 0 is always infinite
Wiki:Coercion /koʊˈɜːrʃən/ is the practice of forcing another party to act in an involuntary manner by use of intimidation or threats or some other form of pressure or force.
like number 1 is int against string which does not fit and forcefully written
It's just to help you understand the logic behind the language.Hope this helps :)