You Don't Know JS - 03 Digging to the Roots of JS
Iteration and iterables, closure, this keyword and object prototypes. 🤯
Iteration permalink
- used for consuming data one chunk at a time
- The iterator pattern defines a data structure called an "iterator" that has a reference to an underlying data source, which exposes a method like
next()
. - The ES6 protocol defines a next() method whose return is an object called an iterator result; the object has value and done properties, where done is a
boolean
that is false until the iteration over the underlying data source is complete. - The data source will be consumed one value at a time, checking after each
next()
call for done to betrue
to stop the iteration.
Consuming iterators permalink
for ... of
loops- spread operator - spread an iterator into an array or an argument list
var vals = [ ...it ];
doSomethingUseful( ...it );
🤔 ...
acts both as a spread operator and a rest parameter?
- Rest parameter: collects all remaining elements into an array.
function add(...args) {
let result = 0;
for (let arg of args) result += arg;
return result
}
- Spread operator: allows iterables( arrays / objects / strings ) to be expanded into single arguments/elements.
const arr = ["Joy", "Wangari", "Warugu"];
const newArr = ["joykare", ...arr];
🤔 Why is map
not considered a default consuming iterator?
- Because with
map
, the iteration is not just over the map's values but instead its entries. - An entry is a tuple (a 2-element array) including both a key and a value.
🤔 What is a Map()
constructor?
new Map([iterable])
- is an iterable of an array or other iterable object whose elements are key-value pairs
let myMap = new Map([
[1, 'one'],
[2, 'two'],
[3, 'three'],
])
Iterables permalink
an iterable is a value that can be iterated over
iterables can be strings, arrays, maps, sets, and others.
For the most part, all built-in iterables in JS have three iterator forms available: keys-only
keys()
, values-onlyvalues()
, and entriesentries()
.Keys are the property names inside of an object.
Values are property values associated with property names.
Entries are the (key-value) pairs of property names and their values.
Closure permalink
- Closure is when a function remembers and continues to access variables from outside its scope, even when the function is executed in a different scope.
- In other words: when a function is defined, it is attached to its enclosing scope via closure.
- Scope is the set of rules that controls how references to variables are resolved.
- Closure is part of the nature of a function. Objects don't get closures. Functions do.
- To observe a closure, you must execute a function in a different scope than where that function was originally defined
- Closure is most common when working with asynchronous code, such as with callbacks.
🤓 Aaaaand another definition:
- Closure is when a function "remembers" its lexical scope even when the function is executed outside that lexical scope.
- Closure doesn't close over a value, nor is it a snapshot - it closes over a variable with a live link.
the this
keyword permalink
this
is not a fixed characteristic of a function based on the function's definition, but rather a dynamic characteristic that's determined each time the function is called (aka depending on the execution context)- again,
this
is not determined by the function definition, but rather by how the function was invoked (aka executed aka()
). - a
this
-aware function can have a different context each time it's called - which makes it more flexible and reusable
🤔 What is an execution context?
- It is a tangible object whose properties are made available to a function while it executes.
🤓 More resources! Understanding the this
keyword explanation by Gordon Zhu
🤔 What are the four different ways of invoking a function?
- implicit binding (the namespace pattern)
call
,apply
,bind
methods- binding with the
new
keyword: thethis
keyword will point at a brand new empty object - the fallback, default binding (global object)
🤯 Arrow functions do not define their own this
keyword, which means that if this
is used inside an arrow function, it will lexically resolve to some enclosing scope that does define the this
keyword (which is the behavior you might want!)
But arrow functions do still have their lexical scope!
🤯 Just because objects use curly braces doesn't mean that they define a new scope, which means that the object's properties aren't lexically scoped.
Prototypes permalink
- Where
this
is a characteristic of function execution, aprototype
is a characteristic of an object, and specifically resolution of property access. - A prototype is a linkage between two objects.
- This prototype linkage occurs when an object is created; it's linked to another object that already exists.
- A series of objects linked together via prototypes is called the prototype chain.
- Objecst are built by constructor calls (via
new
). - A class is a blueprint, and an object is its instance.
- A constructor call makes an object linked to its own prototype.
🤔 What is dunder prototype?
- It's a getter function on
Object.prototype
.
Object Linkage permalink
- To define an object prototype linkage, you can create the object using an
Object.create(..)
utility. Object.create(null)
creates an object that is not prototype-linked anywhere, so it's purely just a standalone object; in some circumstances, that may be preferable.- When we look up an object property, and it doesn't exist, we go up the object chain to look for that property.
- But the cool/magical thing is that
this
will remain the samethis
from the call site.