You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: 1-js/3-object-basics/2-garbage-collection/article.md
+7-8Lines changed: 7 additions & 8 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -151,11 +151,11 @@ Regularly the following "garbage collection" steps are performed:
151
151
152
152
- The garbage collector takes roots and "marks" them.
153
153
- Then it visits and "marks" all references from them.
154
-
- Then it visits marked objects and marks their references (the same object is not visited twice).
155
-
- ...And so on until there are unvisited references.
154
+
- Then it visits marked objects and marks *their* references, but the same object is not visited twice.
155
+
- ...And so on until there are unvisited references (reachable from the roots).
156
156
- All objects except marked ones are removed.
157
157
158
-
For instance, if our object structure might look like this:
158
+
For instance, if our object structure looks like this:
159
159
160
160

161
161
@@ -182,11 +182,10 @@ Javascript engines apply many optimizations to it, to make it run faster and be
182
182
Some of the optimizations:
183
183
184
184
-**Generational collection** -- objects are split into two sets: "new ones" and "old ones". Many objects appear, do their job and die fast, so they can be cleaned up more aggressively. Those "new" that survive for long enough, become "old".
185
-
-**Incremental collection** -- there may be many objects, if we try to clean up the whole object tree at once, it may take some time and introduce visible delays. So the engine tries to split the job into pieces. Then pieces are executed one at a time. That requires some extra bookkeeping in-between to stay consistent.
185
+
-**Incremental collection** -- if there are many objects, and we try to walk and mark the whole object set at once, it may take some time and introduce visible delays. So the engine tries to split the job into pieces. Then pieces are executed one at a time. That requires some extra bookkeeping in-between them to stay consistent.
186
186
-**Idle-time collection** -- the garbage collector tries to run only while the CPU is idle, to reduce the possible effect on the execution.
187
187
188
-
In-depth understanding of these optimization is also achievable, there's no magic, but it requires a lot of under-the-hood digging. Javascript engines implement them differently. And -- what's even more important, things change, so going that deep is recommended when you already know the language well and really need low-level optimizations for your code.
189
-
188
+
In-depth understanding of these optimization is also possible, there's no magic, but it requires a lot of under-the-hood digging. Javascript engines implement garbage collection differently. And -- what's even more important, things change, so going really deep "in advance" is probably not worth that. Unless, of course, it is a matter of pure interest.
190
189
191
190
## Summary
192
191
@@ -197,8 +196,8 @@ The main things to know:
197
196
198
197
Modern engines implement advanced algorithms of garbage collection.
199
198
200
-
If you are familiar with low-level programming, the more detailed information about V8 garbage collector is in the article [A tour of V8: Garbage Collection](http://jayconrod.com/posts/55/a-tour-of-v8-garbage-collection). Also you'd better prepare yourself by learning how values are stored in V8. I'm saying: "V8", because it is best covered with articles in the internet. For other engines, things are partially similar, but not the same.
199
+
If you are familiar with low-level programming, the more detailed information about V8 garbage collector is in the article [A tour of V8: Garbage Collection](http://jayconrod.com/posts/55/a-tour-of-v8-garbage-collection). Also you'd better prepare yourself by learning how values are stored in V8. I'm saying: "V8", because it is best covered with articles in the internet. For other engines, things are somewhat similar, but not the same.
201
200
202
-
In-depth knowledge of engines is good when you need low-level optimizations. It would be wise to plan that as the next step after you're familiar with the language. And when you feel that you need that of course.
201
+
In-depth knowledge of engines is good when you need low-level optimizations. It would be wise to plan that as the next step after you're familiar with the language.
Copy file name to clipboardExpand all lines: 1-js/3-object-basics/6-object-toprimitive/article.md
+1-1Lines changed: 1 addition & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -136,7 +136,7 @@ alert(+user); // 30
136
136
alert(user + 1); // 31 (default like number calls valueOf)
137
137
```
138
138
139
-
If we only want a nice debugging output of our object, then we can implement `toString` only. It the absence of `valueOf` it will be used for both conversions.
139
+
If we want a single "catch-all" place for primitive conversions, or only want a nice debugging output of our object, then we can implement `toString` only. It the absence of `valueOf` it will be used for all conversions.
Functions in Javascript are two-faced. From one side they are callable "actions". From the other side, they are objects.
5
+
6
+
We can add/remove properties to them, and they have some useful properties of their own.
7
+
8
+
## Properties "name" and "length"
9
+
10
+
For Function Declarations, it's obvious:
11
+
12
+
```js run
13
+
functionsayHi() {
14
+
alert("Hi");
15
+
}
16
+
17
+
alert(sayHi.name); // sayHi
18
+
```
19
+
20
+
But what's more funny, the "name"-assigning logic is smart. It also recognizes functions, assigned to variables or provided as object methods:
21
+
22
+
```js run
23
+
letsayHi=function() {
24
+
alert("Hi");
25
+
}
26
+
27
+
alert(sayHi.name); // sayHi (works!)
28
+
```
29
+
30
+
```js run
31
+
let user = {
32
+
33
+
sayHi() { // works
34
+
// ...
35
+
},
36
+
37
+
sayBye:function() { // works too
38
+
// ...
39
+
}
40
+
41
+
}
42
+
43
+
alert(user.sayHi.name); // sayHi
44
+
alert(user.sayBye.name); // sayBye
45
+
```
46
+
47
+
In other cases, the name is empty, like here:
48
+
49
+
```js
50
+
let arr = [function() {}];
51
+
52
+
alert( arr[0].name ); // ""
53
+
```
54
+
55
+
In practice, most functions do have a name. It's mostly used for debugging, or, sometimes,
56
+
57
+
## Builtin "name" and "length"
58
+
59
+
Function objects have
60
+
61
+
We already know that functions in Javascript are objects
62
+
Every value in Javascript has the type. What type of value is a function?
63
+
64
+
In Javascript, a function is an object.
65
+
66
+
NOT ALL !!! (some inherit?)
67
+
68
+
For example, all functions have property `name` (function name) and `length` (number of arguments):
69
+
70
+
```js run
71
+
functionsayHi() {
72
+
alert("Hi");
73
+
}
74
+
75
+
alert( sayHi.name ); // sayHi
76
+
alert( sayHi.length ); // 0
77
+
```
78
+
79
+
80
+
81
+
## Custom properties
82
+
83
+
Using a function as an object is nothing special.
84
+
85
+
Here we add the `counter` property to track the total calls count:
86
+
87
+
```js run
88
+
functionsayHi() {
89
+
alert("Hi");
90
+
91
+
*!*
92
+
// let's count how many times we run
93
+
sayHi.counter++;
94
+
*/!*
95
+
}
96
+
sayHi.counter=0; // initial value
97
+
98
+
sayHi(); // Hi
99
+
sayHi(); // Hi
100
+
101
+
alert( `Called ${sayHi.counter} times` ); // Called 2 times
102
+
```
103
+
104
+
105
+
```warn header="A property is not a variable"
106
+
A property assigned to a function like `sayHi.counter = 0` does *not* define a local variable `counter` inside it. In other words, a property `sayHi.counter` and `let counter` inside the function (if we have it) are two unrelated things.
107
+
108
+
We can treat a function as an object for convenience, store properties in it, that has no effect on its execution.
109
+
```
110
+
111
+
There are many well-known Javascript libraries that make a great use of custom function properties.
112
+
113
+
They create a "main" function and attach many other "helper" functions to it. For instance, the [jquery](https://jquery.com) library creates a function named `$`. The [lodash](https://lodash.com) library creates a function `_`. And then adds `_.clone`, `_.keyBy` and other properties to (see the [docs](https://lodash.com/docs) when you want learn more about them).
114
+
115
+
So, a function can do a useful job by itself and also carry a bunch of other functionality in properties.
Copy file name to clipboardExpand all lines: 1-js/4-more-syntax/2-destructuring-assignment/article.md
+36-20Lines changed: 36 additions & 20 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -40,21 +40,20 @@ alert( title ); // Imperator
40
40
In the code above, the first and second elements of the array are skipped, the third one is assigned to `title`, and the rest is also skipped.
41
41
````
42
42
43
-
### The rest operator
43
+
### The rest '...'
44
44
45
-
If we want not just to get first values, but also to gather all that follows -- we can add one more parameter that gets "the rest" using the rest operator`"..."` (three dots):
45
+
If we want not just to get first values, but also to gather all that follows -- we can add one more parameter that gets "the rest" using the three dots`"..."`:
46
46
47
47
```js run
48
-
*!*
49
-
let [name1, name2, ...rest] = ["Julius", "Caesar", "Consul", "of the Roman Republic"];
50
-
*/!*
48
+
let [name1, name2, *!*...rest*/!*] = ["Julius", "Caesar", *!*"Consul", "of the Roman Republic"*/!*];
51
49
52
50
alert(name1); // Julius
53
51
alert(name2); // Caesar
54
52
55
53
*!*
56
54
alert(rest[0]); // Consul
57
55
alert(rest[1]); // of the Roman Republic
56
+
alert(rest.length); // 2
58
57
*/!*
59
58
```
60
59
@@ -77,14 +76,25 @@ If we want a "default" value to take place of the absent one, we can provide it
77
76
```js run
78
77
*!*
79
78
// default values
80
-
let [name="Guest", surname="Anonymous"] = [];
79
+
let [name="Guest", surname="Anonymous"] = ["Julius"];
81
80
*/!*
82
81
83
-
alert(name); // Guest
84
-
alert(surname); // Anonymous
82
+
alert(name); // Julius (from array)
83
+
alert(surname); // Anonymous (default used)
84
+
```
85
+
86
+
Default values can be more complex expressions or even function calls. They are evaluated only if the value is not provided.
87
+
88
+
For instance, here we use `prompt` function for defaults. But it will run only for the second one, as it's not provided:
89
+
90
+
```js run
91
+
let [name=prompt('name?'), surname=prompt('surname?')] = ["Julius"];
92
+
93
+
alert(name); // Julius (from array)
94
+
alert(surname); // whatever prompt gets
85
95
```
86
96
87
-
Note that default values can be more complex expressions. They are evaluated only if the value is not provided.
97
+
88
98
89
99
## Object destructuring
90
100
@@ -185,7 +195,7 @@ What if the object has more properties than we have variables? Can we assign the
185
195
Unfortunately, the current specification does not support that feature. There is a proposal, but it's not in the standard yet.
186
196
187
197
````smart header="Destructuring without `let`"
188
-
In the examples above variables were declared right before the assignment: `let {…} = {…}`. Of course, we could use the existing variables too. But there's a catch.
198
+
In the examples above variables were declared right before the assignment: `let {…} = {…}`. Of course, we could use existing variables as well. But there's a catch.
189
199
190
200
This won't work:
191
201
```js run
@@ -206,7 +216,7 @@ The problem is that Javascript treats `{...}` in the main code flow (not inside
206
216
}
207
217
```
208
218
209
-
To show Javascript that it's not a code block, but a something else, we can wrap the whole assignment in brackets `(...)`:
219
+
Of course, we want destructuring assignment, but by syntax rules of Javascript blocks are checked first. To show Javascript that it's not a code block, we can wrap the whole assignment in brackets `(...)`:
210
220
211
221
212
222
```js run
@@ -218,6 +228,7 @@ let title, width, height;
218
228
219
229
alert( title ); // Menu
220
230
```
231
+
Brackets do not affect the result, but now the `{...}` thing is not in the main code flow, so code block syntax does not apply, and the engine finally understands it right.
221
232
````
222
233
223
234
## Nested destructuring
@@ -232,7 +243,8 @@ let options = {
232
243
width:100,
233
244
height:200
234
245
},
235
-
items: ["Cake", "Donut"]
246
+
items: ["Cake", "Donut"],
247
+
extra:true// something extra that we will not destruct
236
248
}
237
249
238
250
// destructuring assignment on multiple lines for clarity
@@ -242,7 +254,7 @@ let {
242
254
height
243
255
},
244
256
items: [item1, item2], // assign items here
245
-
title ="Menu"//an extra property (default value is used)
257
+
title ="Menu"//not present in the object (default value is used)
246
258
} = options;
247
259
248
260
alert(title); // Menu
@@ -252,11 +264,13 @@ alert(item1); // Cake
252
264
alert(item2); // Donut
253
265
```
254
266
255
-
As we can see, the whole `options` object is correctly assigned to variables.
267
+
The whole `options` object except `extra` that was not mentioned, is assigned to corresponding variables.
256
268
257
-
The left part of the destructuring assignment can combine and nest things as needed.
269
+

258
270
259
-
## Destructuring function parameters
271
+
As we can see, the left part of the destructuring assignment can combine and nest things as needed.
272
+
273
+
## Smart function parameters
260
274
261
275
There are times when a function may have many parameters, most of which are optional. That's especially true for user interfaces. Imagine a function that creates a menu. It may have a width, a height, a title, items list and so on.
262
276
@@ -283,14 +297,16 @@ Destructuring comes to the rescue!
283
297
We can pass parameters as an object, and the function immediately destructurizes them into variables:
0 commit comments