Skip to content

Add concept exercise conditionals #1037

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 25 commits into from
Mar 16, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
106 changes: 83 additions & 23 deletions concepts/comparison/about.md
Original file line number Diff line number Diff line change
@@ -1,44 +1,104 @@
# About

TODO: this is a stub that needs more information
## Comparing Numbers

## Comparing numbers
In JavaScript numbers can be compared using the following relational and equality operators.

Numbers are considered equal if they have the same value.
| Comparison | Operator |
| ---------------------- | --------- |
| Greater than | `a > b` |
| Greater than or equals | `a >= b` |
| Less than | `a < b` |
| Less than or equals | `a <= b` |
| (Strict) Equals | `a === b` |
| Not (strict) equals | `a !== b` |

The result of the comparison is always a boolean value, so either `true` or `false`.

```javascript
1 == 1.0;
1 < 3;
// => true

2 !== 2;
// => false

1 === 1.0;
// => true
// Remember, all numbers are floating-points, so this is different syntax for
// All numbers are floating-points, so this is different syntax for
// the exact same value.
```

1 === 1n;
## Comparing Strings

In JavaScript the comparison operators above can also be used to compare strings.
In that case a dictionary (lexicographical) order is applied.
You can find a list of the exact order of all the characters [here][utf-16-list].

```javascript
'Apple' > 'Pear';
// => false
// Strictly checking a number against a bigint will always result in false.

1 == 1n;
'a' < 'above';
// => true
// A number is equal to a bigint if they represent the same value.

1.0 == 1n;
'a' === 'A';
// => false
```

You need to be careful when you compare two variables that appear to contain numeric values but are of type string.
Due to the dictionary order the result will not be the same as comparing values of type number.

```javascript
10 < 2;
// => false

'10' < '2';
// => true (because "1" comes before "2")
```

Another way to compare strings is the [localeCompare][mdn-locale-compare] method.
It allows to set a variety of [options][mdn-locale-compare-options] to adjust the way strings are compared.

## Strict Equality

You might wonder about the three equal signs for checking equality in JavaScript.
`===` represents the check for _strict equality_ which means that no type conversion is performed and values of different types are always unequal.

```javascript
'3' === 3;
// => false
// The value on the left has type string, the value on the right has type number.

1 === 1n;
// => false
// The value on the left has type number, the value on the right has type bigint.
```

Using `===` and `!==` is the recommended way of checking equality in JavaScript.

## Avoiding Implicit Type Conversion

There is also `==` and `!=` which represents checking for _loose equality_.
You should avoid it because it will apply implicit type conversion before performing the comparison.
The outcomes in these cases are hard to predict and sometimes not what you would expect.
You can read more about it [here][mdn-loose-equals].

```javascript
0 == false;
// => true
// A number is equal to a bigint if they represent the same value.
```

There are different outcomes when comparing numbers with different types.
In general, only two operands of the type `number` can ever be _strictly equal_ (`===`), and the following can be used for _loose equality_ (`==`):
In theory you can also compare values of different types (e.g., `"1" < 2`).
Then the values will be implicitly converted to determine whether the result is true or false.
Just as checking for loose equality, this is also not recommended for the same reason as mentioned above.

| A | B | `==` |
| ------ | --------- | --------------------- |
| Number | Undefined | `false` |
| Number | Null | `false` |
| Number | Number | `A === B` |
| Number | String | `A === ToNumber(B)` |
| Number | Boolean | `A === ToNumber(B)` |
| Number | Object | `A == ToPrimitive(B)` |
What should you do instead?
You can apply [explicit type conversion][concept-type-conversion].
With that you can then ensure values have the correct type before performing the comparison.
Then your code will be easier to understand and less error prone.

- `ToNumber(X)` attempts to convert its argument `X` to a `number` before comparison. It is equivalent to `+B` (the unary `+` operator).
- `ToPrimitive(X)` attempts to convert its object argument `X` to a primitive value, by attempting to invoke varying sequences of `X.toString` and `X.valueOf` methods on `X`.
[mdn-loose-equals]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Equality
[concept-type-conversion]: /tracks/javascript/concepts/type-conversion
[utf-16-list]: https://www.fileformat.info/info/charset/UTF-16/list.htm
[mdn-locale-compare]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/localeCompare
[mdn-locale-compare-options]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/Collator/Collator#parameters
73 changes: 73 additions & 0 deletions concepts/comparison/introduction.md
Original file line number Diff line number Diff line change
@@ -1 +1,74 @@
# Introduction

## Comparing Numbers

In JavaScript numbers can be compared using the following relational and equality operators.

| Comparison | Operator |
| ---------------------- | --------- |
| Greater than | `a > b` |
| Greater than or equals | `a >= b` |
| Less than | `a < b` |
| Less than or equals | `a <= b` |
| (Strict) Equals | `a === b` |
| Not (strict) equals | `a !== b` |

The result of the comparison is always a boolean value, so either `true` or `false`.

```javascript
1 < 3;
// => true

2 !== 2;
// => false

1 === 1.0;
// => true
// All numbers are floating-points, so this is different syntax for
// the exact same value.
```

## Comparing Strings

In JavaScript the comparison operators above can also be used to compare strings.
In that case a dictionary (lexicographical) order is applied.
You can find a list of the exact order of all the characters [here][utf-16-list].

```javascript
'Apple' > 'Pear';
// => false

'a' < 'above';
// => true

'a' === 'A';
// => false
```

## Strict Equality

You might wonder about the three equal signs for checking equality in JavaScript.
`===` represents the check for _strict equality_ which means that no type conversion is performed and values of different types are always unequal.

```javascript
'3' === 3;
// => false
// The value on the left has type string, the value on the right has type number.

1 === 1n;
// => false
// The value on the left has type number, the value on the right has type bigint.
```

Using `===` and `!==` is the recommended way of checking equality in JavaScript.

There is also `==` and `!=` which represents checking for _loose equality_.
You should avoid it because it will apply implicit type conversion before performing the comparison.
The outcomes in these cases are hard to predict and sometimes not what you would expect.

```javascript
0 == false;
// => true
```

[utf-16-list]: https://www.fileformat.info/info/charset/UTF-16/list.htm
15 changes: 14 additions & 1 deletion concepts/comparison/links.json
Original file line number Diff line number Diff line change
@@ -1 +1,14 @@
[]
[
{
"url": "https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators#relational_operators",
"description": "MDN: Relational operators"
},
{
"url": "https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators#equality_operators",
"description": "MDN: Equality operators"
},
{
"url": "https://www.fileformat.info/info/charset/UTF-16/list.htm",
"description": "List of UTF-16 character order"
}
]
140 changes: 139 additions & 1 deletion concepts/conditionals/about.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,141 @@
# About

TODO: add information on conditionals concept
## General Syntax

A common way to conditionally execute logic in JavaScript is the if-statement.
It consists of the `if` keyword, a condition wrapped in round brackets and a code block wrapped in curly brackets.
The code block will only be executed if the condition evaluates to `true`.

```javascript
if (condition) {
// code that is executed if "condition" is true
}
```

It can be used stand-alone or combined with the `else` keyword.

```javascript
if (condition) {
// code that is executed if "condition" is true
} else {
// code that is executed otherwise
}
```

## Nested If-Statements

To nest another condition into the `else` statement you can use `else if`.
Note that there is no `elseif` keyword in JavaScript.
Instead write `else` followed by another `if` statement.

```javascript
if (condition1) {
// code that is executed if "condition1" is true
} else if (condition2) {
// code that is executed if "condition2" is true
// but "condition1" was false
} else {
// code that is executed otherwise
}
```

Theoretically you can nest as many additional conditions as you want.
In practice you would use a [`switch` statement](/tracks/javascript/concepts/conditionals-switch) instead in these cases.

```javascript
if (condition1) {
// ...
} else if (condition2) {
// ...
} else if (condition3) {
// ...
} else if (condition4) {
// ...
} else {
// ...
}
```

## Condition

When constructing complex conditions, refer to the [operator precedence table][mdn-operator-precedence] to avoid unnecessary brackets.

```javascript
if (num >= 0 && num < 1) {
// ...
}

// The inner brackets are obsolete because relational operators
// have higher precedence than logical operators.
if (num >= 0 && num < 1) {
// ...
}
```

Also consider using additional variables to make the code more readable.

```javascript
const isPositive = num >= 0;
const isSmall = num < 1;
if (isPositive && isSmall) {
// ...
}
```

In JavaScript the condition does not have to be of type boolean.
If any other type than boolean is provided in a boolean context like the if-statement, JavaScript will implicitly convert the value to boolean.
Refer to the [type coercion concept][concept-type-coercion] for details on which values are _truthy_ and _falsy_, respectively.

```javascript
const num = 4;
if (num) {
// this code block will be executed because 4 is truthy
}
```

## Short-Hand Notations

If you only want to execute one statement in the code block for `if` or `else`, it is possible in JavaScript to omit the curly brackets.

<!-- prettier-ignore-start -->
```javascript
if (condition) doSomething();

// or

if (condition)
doSomething();
```
<!-- prettier-ignore-end -->

This is sometimes used when checking for an error condition for example.
In general it is not recommended because it is easy to forget to add the brackets back in when adding a second statement that should depend on the same condition.

When writing functions, it is a common pattern to omit the `else` block and use an early `return` in the `if` block instead.
In many cases this reduces _nesting_ and makes the code more readable and easier to follow.

```javascript
function checkNumber(num) {
let message = '';

if (num === 0) {
message = 'You passed 0, please provide another number.';
} else {
message = 'Thanks for passing such a nice number.';
}

return message;
}

// Can also be written as ...
function checkNumber(num) {
if (num === 0) {
return 'You passed 0, please provide another number.';
}

return 'Thanks for passing such a nice number.';
}
```

[concept-type-coercion]: /tracks/javascript/concepts/type-coercion
[mdn-operator-precedence]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Operator_Precedence#table
33 changes: 32 additions & 1 deletion concepts/conditionals/introduction.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,34 @@
# Introduction

TODO: add introduction for conditionals concept
A common way to conditionally execute logic in JavaScript is the if-statement.
It consists of the `if` keyword, a condition wrapped in round brackets and a code block wrapped in curly brackets.
The code block will only be executed if the condition evaluates to `true`.

```javascript
if (condition) {
// code that is executed if "condition" is true
}
```

It can be used stand-alone or combined with the `else` keyword.

```javascript
if (condition) {
// code that is executed if "condition" is true
} else {
// code that is executed otherwise
}
```

To nest another condition into the `else` statement you can use `else if`.

```javascript
if (condition1) {
// code that is executed if "condition1" is true
} else if (condition2) {
// code that is executed if "condition2" is true
// but "condition1" was false
} else {
// code that is executed otherwise
}
```
Loading