preface
Chinese Lunar 2019 has passed, while before going to work this period of time, sorted out the basic knowledge of javascript, here to share with you, like the big guys can give a small thumbs-up. I am making: github.com/Michael-lzg
Related articles:
Js is a single threaded language. The JS engine has one main thread that interprets and executes js programs, and there are actually other threads. For example: threads that handle Ajax requests, threads that handle DOM events, timer threads, threads that read and write files (for example in Node.js), and so on. These threads may exist inside or outside the JS engine, but we don’t make that distinction here. Call them worker threads.
JS execution context
When code is run, a corresponding execution environment is generated. In this environment, all variables are raised beforehand (variable promotion), some are assigned directly, some are undefined by default, and the code is executed from the top down, which is called the execution context.
Example 1: Variable promotion
foo // undefined
var foo = function() {
console.log('foo1')
}
foo() // foo1, foo is assigned
var foo = function() {
console.log('foo2')
}
foo() // reassign foo2, foo
Copy the code
Example 2: Function promotion
foo() // foo2
function foo() {
console.log('foo1')
}
foo() // foo2
function foo() {
console.log('foo2')
}
foo() // foo2
Copy the code
Example 3: Declare priority, function > variable
foo() // foo2
var foo = function() {
console.log('foo1')
}
foo() // reassign foo1, foo
function foo() {
console.log('foo2')
}
foo() // foo1
Copy the code
Runtime environment
In the JavaScript world, there are three running environments:
- Global environment: The environment that code enters first
- Function context: The context in which a function is executed when called
- Eval function :(not often used)
Execution context characteristics
- Single-threaded, running on the main process
- Synchronous execution, executed from top to bottom in sequence
- There is only one global context, which is ejected from the stack when the browser closes
- There is no limit to the number of execution contexts for a function
- Each time a function is called, a new execution context is created
Execution context stack
An execution context is generated when global code is executed, and again every time a function is called. When the function call completes, the context and its data are eliminated and returned to the global context. There is only one execution context that is active.
This is actually a process of pushing out the stack — executing the context stack.
var // 1. Enter the global context
a = 10,
fn,
bar = function(x) {
var b = 20
fn(x + b) // 3. Access the FN context
}
fn = function(y) {
var c = 20
console.log(y + c)
}
bar(5) // 2. Enter the bar context
Copy the code
Execute the context life cycle
1. Creation phase
- Generating variable objects
- Establish scope chains
- Make sure this points to
2. Execution phase
- Variable assignment
- Function reference
- Execute other code
3. Destruction stage
- Execute out of the stack and wait for the collection to be destroyed
Javascript event loop
- Synchronous and asynchronous tasks enter different execution “places”, synchronous to the main thread, asynchronous to the main thread
Event Table
And register the function. - When the assigned task is complete,
Event Table
I’m going to move this function inEvent Queue
. - Tasks in the main thread are empty and go
Event Queue
Read the corresponding function, into the main thread execution. - The above process is repeated over and over again, as is often said
Event Loop
(Event loop).
Synchronous and asynchronous tasks, we have a more detailed definition of tasks:
Macro-task:
It is understood that each execution stack executes code that is a macro task (including fetching event callbacks from the event queue and placing them on the execution stack each time).
In order to keep internal MACRO tasks and DOM tasks in order, browsers will re-render the page after the end of one Macro task and before the start of the next.
(Macro) Task: Script, setTimeout, setInterval, I/O, UI interaction events, postMessage, MessageChannel, setImmediate(node.js)
Micro-task:
A task that is executed immediately after the execution of the current task. That is, after the current task, before the next task, and before rendering. So it responds faster than setTimeout (setTimeout is task) because there is no need to wait for rendering. That is, after a macroTask has been executed, all microTasks created during its execution have been executed (before rendering).
Microtasks mainly include promise. then, MutaionObserver, and process.nexttick (node.js environment).
For example
Let’s take a look at some of the more complex code and see if you really understand how JS works:
console.log('1')
setTimeout(function() {
console.log('2')
process.nextTick(function() {
console.log('3')})new Promise(function(resolve) {
console.log('4')
resolve()
}).then(function() {
console.log('5')
})
})
process.nextTick(function() {
console.log('6')})new Promise(function(resolve) {
console.log('7')
resolve()
}).then(function() {
console.log('8')})setTimeout(function() {
console.log('9')
process.nextTick(function() {
console.log('10')})new Promise(function(resolve) {
console.log('11')
resolve()
}).then(function() {
console.log('12')})})/ / 1,7,8,2,4,5,6,3,9,11,12,10
Copy the code
Another section
async function async1() {
console.log('async1 start')
await async2()
console.log('async1 end')}async function async2() {
console.log('async2')}console.log('script start')
setTimeout(function() {
console.log('setTimeout')},0)
async1()
new Promise(function(resolve) {
console.log('promise1')
resolve()
}).then(function() {
console.log('promise2')})console.log('script end')
// script start
// async1 start
// async2
// promise1
// script end
// async1 end
// promise2
// setTimeout
Copy the code
Solutions to asynchronous problems
- The callback function
ajax('XXX1'.() = > {
// Callback function body
ajax('XXX2'.() = > {
// Callback function body
ajax('XXX3'.() = > {
// Callback function body})})})Copy the code
- Advantages: Solves the synchronization problem
- Cons: Callback hell, no try catch, no return
2. Promise was created to solve the problem of callback.
Promise implements chained calls, which means that each time we return a new Promise after then, if we return in then, the result of the return will be wrapped by promise.resolve ().
- Pros: Solved the callback hell problem
- Disadvantages: Promise cannot be cancelled and errors need to be caught through callback functions
3, Async/await
- The advantage is that the code is clean, you don’t have to write a bunch of then chains like Promise, and you handle callback hell
- Disadvantages: await transforms asynchronous code into synchronous code, and using await results in performance degradation if multiple asynchronous operations have no dependencies.
conclusion
- Javascript is a single-threaded language
- Event Loop is the execution mechanism of javascript
Node environment and browser differences
1. The direction of this in the global context
- In node, this points to global
- In the browser this points to the window
- That’s why underscore initially defines a root;
The browser window encapsulates a number of APIS such as alert, document, location, history, etc. We can not XXX () in the node environment; Or Windows. XXX (); . Because these apis are browser-level wrappers, they don’t exist in javascript. Of course, Node also provides a number of Node-specific apis.
2. Js engine
-
In browsers, different vendors provide different browser kernels, and browsers rely on these kernels to interpret the JS we write. But given the small differences between kernels, we needed compatibility so that there were some good libraries to help us deal with this problem. Like jquery, underscore, and so on.
-
Nodejs is based on Chrome’s JavaScript Runtime, which means it’s essentially a wrapper around the Google Chrome 8 engine. The V8 engine executes Javascript very fast and performs very well.
3. DOM manipulation
- Js in browsers mostly manipulate the DOM directly or indirectly (some virtual DOM libraries and frameworks). Because the code in the browser works primarily at the presentation level.
- Node is a server-side technology. There is no foreground page, so we will not manipulate the DOM in Node.
4. I/O Reading and writing
Unlike browsers, which need to read and write files like other server-side technologies, NodeJS provides a convenient component. Browsers (to ensure compatibility) have a lot of trouble opening a local image directly in the page (don’t tell me this is not easy, relative path… You’ll see if you can either find a library or binary stream or upload it so that the network address is displayed. Why else would they build a JS library), while Node does all this with a component.
5. Module loading
-
One of the features of javascript is that there is no native API that provides package references to execute everything at once, depending on the skill of your closures. Use things together, not divide and conquer, do not have logic and reuse. If the page is simple or a website, of course, we can use some AMD, CMD JS libraries (such as requireJS and seaJS) to do this. In fact, many large websites do.
-
NodeJS provides an API for loading CMD modules, so if you’ve used seaJS before, you should be up to speed. Node also provides a package management tool called NPM, which makes it easier to manage our drinking libraries