JavaScript Type Conversion & Coercion Explained
Tags: codenewbie, javascript, webdev, beginners
Published: 2021-12-19 19:21:41

To properly write JavaScript, we need to be able to understand what's going on under the hood. Since JavaScript is a dynamically typed language, it has many *weird* parts. You don't have to specify the type of some value before you use it. It allows you to change the types as you write your code. 

Let's say you declare a variable and assign it to a `string`. Later on, you can decide to change it to a `number`. As I discussed in my post about [null vs. undefined](https://blog.zahrakhadijha.com/the-difference-between-null-and-undefined-in-javascript), you can leave a variable empty and initialize it later without specifying it's type. This could create a lot of buggy behavior in JavaScript (aren't we thankful TypeScript exists? 😜)

**Type Coercion vs. Conversion** is one of the topics that can be hard to understand because the language behaves in strange ways. When comparing the string `'28'` to the number `28`, you'd think that they're the same. When you compare them loosely, `'28' == 28` you get that they're the same. But they're not. JavaScript does *implicit coercion* under the hood which converts `'28' == 28` to `28 == 28` which obviously becomes `true`.

## Introduction

To understand Type Coercion, we need to remember that JavaScript generally has two types: **Primitives** and **Objects**. 

There are [7 primitive data types](https://developer.mozilla.org/en-US/docs/Glossary/Primitive): string, number, boolean, symbol, bigint, undefined, and null. These are not objects and they don't have built-in methods.

[Objects](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object) are everything else.

Type Conversion happens in two different ways:

## Implicit Coercion 

Implicit coercion happens automatically by JavaScript. The compiler goes behind your back and converts a value without you explicitly telling it to. It's completely hidden from you. For example, if you add a `string` to a `number` or vice versa, JavaScript will automatically concatenate it to a `string`. Or if you apply non-numbers to mathematical expressions, they will be converted to `numbers`. This is called Type Conversion.

Let's look at some code:

```javascript
const currentYear = 2021
const age = '28'
console.log(currentYear + age) // '202128'
```

JavaScript converted the number `2021` to a string by concatenating the string `'28'` giving you a result of `202128` instead of doing an actual calculation. 

Another example, WITH subtraction:

```javascript
let age = '28'
let currentYear = '2021'
console.log(currentYear - age) // the strings are implicitly coerced to 1993 here 
```

This performed a mathematical calculation and implicitly converted the strings into a `number`.

## Explicit Coercion

Explicit coercion happens when you convert the data type of a value stored in a variable ON PURPOSE (explicitly) with a built-in method. You can visually see it happening in your code. JavaScript has three explicit type conversions: 

1. `Number()`
2. `String()`
3. `Boolean()`

You cannot convert a variable to `null` or `undefined`. I will only be explaining a high-level overview of the three methods. If you'd like to dive deeper, please read [YDKJS](https://github.com/getify/You-Dont-Know-JS/blob/1st-ed/types%20%26%20grammar/ch4.md) as the book goes into a rabbit hole of explaining every bit.

### Number()

The `Number()` method will convert any non-number value into a number. It's a little bit complicated because if you convert `Number(true)` it becomes `1`, `Number(false)` is `0`, `Number(undefined)` is `NaN` and `Number(null)` is `0`. 👀 

`Number()` will convert a random string, such as `Number('Zahra')` to `NaN`.

```javascript
let age = '28'
Number(age) // 28 - it will be converted from a string to the number 28

let currentYear = 2021
console.log(Number(age) + 2021) // 2049 - does the mathematical calculation and prints out a number

console.log(currentYear + age) // `202128' - prints out the concatenated string without explicit conversion.

```

### String()

The `String()` method will convert any non-string value into a string representation. Unlike the `Number()` method, `String()` will convert `String(null) to 'null'`, `String(undefined)` to `'undefined'`, `String(true)` to `'true'` and `String(false)` to `'false'`.

The `String()` method can be explicit or it can be automatic if a non-string is used in a way where it will be coerced. The most straightforward thing about this method is that the value stays as it is but the data type changes to a `string.`

```javascript
let age = 28 
String(age) // '28'

let coffee = 2 + " cups"
String(coffee) // '2 cups' - it was already coerced to a string beforehand and will stay a string with the method

let nothing = null
String(nothing) // 'null'

```

### Boolean()

The `Boolean()` method is an interesting one! JavaScript already has boolean keywords `true` and `false` but there is a list of values that will ALWAYS be falsy when you force a `Boolean()` coercion on them:

- `undefined`
- `null`
- `false`
- `+0`, `-0`, and `NaN`
- `""`

Everything else NOT on this list is considered a truthy value. Let's look at some code:

```javascript
let emptyArray = [] 
let emptyObject = {}
let emptyFunction = function(){}

Boolean(emptyArray) // true
Boolean(emptyObject) // true
Boolean(emptyFunction) // true
```

These are all true because they're not on the list of falsey values. The importance of boolean values is in understanding how the value will behave if you coerce it. 

## Summary 

There is A LOT more to this subject and I recommend reading YDKJS to get a deeper understanding of the topic. Even though this subject is a bit confusing (this was a hard blog post to write), it's important to understand the buggy parts so that you understand how JavaScript behaves to write better code.

Yes, we have TypeScript now to eliminate some of these bugs so if you wanted to, you could just start using TypeScript but I find it interesting to learn about these weird parts of JavaScript.

I hope this post helped somewhat! I can be reached on [Twitter](https://twitter.com/zahrakhadijha) so feel free to DM if you have questions!

### Resources:

1. [YDKJS: Types & Grammar](https://github.com/getify/You-Dont-Know-JS/blob/1st-ed/types%20%26%20grammar/ch4.md)
2. [DEV](https://dev.to/alexdevero/how-type-coercion-in-javascript-works-5263)
3. [MDN](https://developer.mozilla.org/en-US/docs/Glossary/Type_coercion)
4. [freeCodeCamp](https://www.freecodecamp.org/news/js-type-coercion-explained-27ba3d9a2839/)