asynchronous

  • Cause of occurrence
    • JavaScript is executed in a single-threaded environment.
    • Single-threaded means that you can only complete one task at a time. If there are multiple tasks, they must be queued, the first task completed, the next task executed, and so on.
    • The advantage of single-threaded mode is that it is relatively simple to implement and the execution environment is single. The disadvantage is that as long as one task takes a long time, subsequent tasks must wait in line, which will delay the execution of the entire program. A common browser non-response (suspended animation) is usually the result of a single piece of JavaScript code running for so long (such as an infinite loop) that the entire page gets stuck in one place and no other task can be performed.
    • To solve this problem, the JavaScript language divides the execution modes of tasks into two types, synchronous and asynchronous.
  • Asynchronous usage scenarios
    • Ajax operation
  • Implementation of asynchronous programming
    • The callback function

      • Advantages: Simple, easy to understand and deploy.
      • Cons: bad to read and maintain, highly coupled parts, messy process, and only one callback per task can be specified.
      • Code implementation
        Function f2(c) {console.log(c, 'hehe'); function f2(c, 'hehe') {console.log(c, 'hehe'); } function f1(callback) {setTimeout(function() {// f1 taskcode console.log('f1 done '); Callback ('f2 start execution ', 'hehe'); }, 1000); } f1(f2);Copy the code
    • Event listeners

      • Code implementation
      • Advantages: Easy to understand, multiple events can be bound, each event can specify multiple callback functions, and can be “decouple”, which is good for modularity.
      • Disadvantages: The entire program becomes event-driven, and the flow becomes very fluid.
        f1.on('done', f2);
        Copy the code
    • Publish/subscribe

      • Definition: We assume that there is a “signal center” that “publishes” a signal when a task completes, and that other tasks can “subscribe” the entire signal to the signal center to know when they can start executing. This is called the publish/subscribe model, or the Observer model.
      • Advantages:
        • This approach is similar in nature to “event listening”, but clearly superior to the latter. Because we can monitor the application by looking at the “message center” to see how many signals exist and how many subscribers each signal has.
        • One is decoupling in time, but decoupling in objects
        • It can be used in asynchronous programming, or it can be used in code that helps us achieve looser coupling
      • Disadvantages:
        • Creating a subscriber itself takes time and memory
        • When you subscribe to a message, the next message may not happen, but the subscriber is always in memory
        • The observer mode weakens the relationship between objects, which is a good thing, but if overused, the relationship between objects can be hidden, making the project difficult to track, maintain and understand.
      • Usage scenarios
        • DOM events
        • Custom events
      • Code implementation
        Function Event() {// Store different Event types corresponding to different handlers, to ensure that subsequent emMIT can execute. this.cache = {}; Prototype. On = function(type, handle) {if(! this.cache[type]) { this.cache[type] = [handle]; }else { this.cache[type].push(handle); Prototype = function() {var type = [0], arg = [].slice.call(arguments, 1); for(var i = 0; i < this.cache[type].length; i++) { this.cache[type][i].apply(this, arg); if(this.cache[type][i].flag) { this.cache[type].splice(i, 1); if(this.cache[type][i].flag) { this.cache[type].splice(i, 1); }}}} // Remove an event.prototype. empty = function(type) {this.cache[type] = []; Function (type, handle) {this.cache[type] = this.cache[type].filter((ele) => ele! = handle); Prototype. Once = function(type, handle) {if(! this.cache[type]) { this.cache[type] = []; } // flag handle.flag = true; this.cache[type].push(handle); } function detail1(time) { console.log('overtime1' + time); } function detail2(time) { console.log('overtime2' + time); } var oE = new Event(); oE.on('over', detail1); oE.on('over', detail2); oE.emmit('over', '2019-11-11'); oE.remove('over', detail2); oE.emmit('over', 'second-11-11');Copy the code
    • Promise object

      • define
        • CommonJS is a specification developed by the CommonJS working group to provide a unified interface for asynchronous programming.
        • In a nutshell, the idea is that each asynchronous task returns a Promise object with a then method that allows the callback function to be specified.
      • Advantages:
        • The callbacks become chained, the flow of the program can be seen clearly, and there is a whole set of methods for the flow.
        • Moreover, it has one advantage that none of the previous three methods have: if a task is already complete and a callback function is added, the callback function is executed immediately. So don’t worry about missing an event or signal.
      • Disadvantages: is to write and understand, relatively difficult.

Promise,

  • Definition: Promises are a solution to asynchronous programming. Promises are simply containers that hold the results of events that will end in the future.
  • The characteristics of
    • The Promise object represents an asynchronous operation, with three states: Pending, Resolve and Rejected. Only the result of the asynchronous operation can change the state, and none of the other operations can change the state.
    • Once the state has changed, it can never change again, and you can get this result at any time. The state of a Promise object has only two possibilities: Pending->Resolve or Pending->Resolve, and as long as both occur, the result will remain the same, unlike event listening, which is characterized by different times.
  • Disadvantages:
    • First, you can’t cancel a Promise. Once it’s created, it’s executed immediately.
    • Second, if the callback function is not set, errors thrown internally by a Promise are not reflected externally
    • Finally, when you are in a Pending state, you cannot tell what stage you are in.
  • The source code to achieve
    • function
      • synchronous
      • asynchronous
      • Then chain operation
        • Processing returns the normal value
        • The handler returns a Promise value
      • Then asynchronous operation
      • Then catch error
      • Empty then
      • Promise.all() : All success, one failure, all failure
      • Promise.race() : Whichever state changes, the state of P changes
      function MyPromise(executor) { var self = this; self.status = 'pending'; self.resolveValue = null; self.rejectReason = null; self.resolveCallBackList = []; self.RejectCallBackList = []; function resolve(value) { if(self.status === 'pending') { self.status = 'Fulfilled'; self.resolveValue = value; self.resolveCallBackList.forEach(function(ele) { ele(); }); } } function reject(reason) { if(self.status === 'pending') { self.status = 'Rejected'; self.rejectReason = reason; self.RejectCallBackList.forEach(function(ele) { ele(); }) } } try { executor(resolve, reject); }catch(e) { reject(e); } } function ResolutionReturnPromise(nextPromise, returnValue, res, rej) { if(returnValue instanceof MyPromise) { returnValue.then(function() { res(val); }, function(reason) { rej(reason); }) }else { res(returnValue); } } MyPromise.prototype.then = function(onFulfilled, onRejected) { if(! onFulfilled) { onFulfilled = function(val) { return val; } } if(! onRejected) { onRejected = function(reason) { throw new Error(reason); } } var self = this; var nextPromise = new MyPromise(function(res, rej) { if(self.status === 'Fulfilled') { setTimeout(function() { try { var nextResolveValue = onFulfilled(self.resolveValue); ResolutionReturnPromise(nextPromise, nextResolveValue, res, rej); }catch(e) { rej(e); }}, 0); } if(self.status === 'Rejected') { setTimeout(function() { try{ var nextResolveValue = onRejected(self.rejectReason); ResolutionReturnPromise(nextPromise, nextRejectValue, res, rej); }catch(e) { rej(e); } }) } if(self.status === 'pending') { self.resolveCallBackList.push(function() { setTimeout(function() { try { var nextResolveValue = onFulfilled(self.resolveValue); ResolutionReturnPromise(nextPromise, nextResolveValue, res, rej); }catch(e) { rej(e); } }, 0) }) } }) return nextPromise; } MyPromise.race = function(promiseArr) { return new Promise(function(resolve, reject) { promiseArr.forEach(function(promise, index) { promise.then(resolve, reject); })})}Copy the code
  • Usage scenarios
    • An Ajax request
      • Definition:
        • Ajax is an acronym for Asynchronous javascript and XML, in which javascript is used to manipulate XML (and now JSON) in an Asynchronous manner. With the advent of Google Maps, this way of communicating with servers without a page refresh quickly became known. In the traditional Web model, a client sends a request to a server, and the server returns the entire page.
        • The way we learned about transferring data from a form form is in the traditional Web model. When we click the Submit button, the entire page is refreshed. The form has three important properties: Method, Action, and encType. Method is the method of data transmission, usually GET or POST, Action is the address we send data to, encType default value is “application/ X-www-form-urlencoded “, that is, all characters are coded before sending, This property value is the default even if we don’t write it. However, when using a form that contains a file upload control, this value must be changed to “multipart/form-data”, meaning that no characters are encoded. In the Ajax model, data is transferred independently between the client and the server, and the server no longer returns the entire page.
      • advantages
        • The page is not refreshed, and users can communicate with the server on the page, providing better user experience.
        • Asynchronous communication with the server does not interrupt user operations, providing better user experience.
        • Lighten the load on the server.
        • No plug-ins or applets are required
      • disadvantages
        • The browser’s back mechanism is not supported
        • Security problems, cross-site scripting attacks, SQL injection attacks
        • Weak search engine support
        • Mobile devices are not supported
        • Defeats the purpose of URL and resource location
      • Object properties
        • Onreadystatechange: statechange trigger
        • ReadyState: object state
          • 0: indicates initialization, at which point an XMLHttpRequest object is created
          • 1: reading. The code has called the open method of XMLHttpRequest and the XMLHttpRequest has sent the request to the server.
          • 2: indicates that it has been read. At this point, a request has been sent to the server through the open method, but it has not been received.
          • 3: indicates that the HTTP response header information is received, but the message body information is not fully received.
          • 4: indicates complete. The response has been fully accepted
        • ResponseText: The text version of the data returned by the server process
        • ResponseXML: DOM-compliant XML text object that the server process returns data to
        • Status: indicates the status code returned by the server
      • Code implementation
        function AJAX(json) { var url = json.url, method = json.method, flag = json.flag, data = json.data, callBack = json.callBack, xhr = null; If (window.xmlhttprequest) {XHR = new window.xmlhttprequest (); }else {// IE6 below use this XHR = new ActiveXObject(' microsoft.xmlhttp '); Xhr.onreadystatechange = function() {if(xhr.readyState === 4 &&xhr.status === 200) {// Data is available callBack(xhr.responsetext); If (method === 'get') {url += '? ' + data + new Data().getTime(); Xhr. open('get', url, flag); xhr.send(); }else { xhr.open('post', url, flag); // 4. Set the request header xhr.setrequesTheader (' content-type ', 'application/x-www-form-urlencoded'); // 5. Set the request body xhr.send(data); }}Copy the code
    • Custom popup processing
    • Image to load

Generator

  • Definition: Generator, itself a function, returns an iterated object after execution, uses Generator functions with Yeild inside the function, executes in segments, and suspends when encountering Yeild.
  • The characteristics of
    • * is required between function and function name
    • Function body internal Yeild expression, output different internal states (values)
    • You can surrender execution of a function
  • Role: Work with Promise to solve the callback hell problem
  • Cooperate with the library
    • Co
  • Usage scenarios
    • You can deploy the Iterator interface on any object, working with the Promise and Co libraries to solve callback hell.

async

  • Definition: is a Generator syntax sugar. After compiling with Babel, we can see that it is a Generator+Promise+Co recursive idea. Use with await.
  • Purpose: Gracefully solve the problem of asynchronous operation
    • Asynchronous programming can cause problems
      • The callback hell
        // If you can write multiple callback functions, you will find that it is not elegant to write multiple callback functions, a bunch of.then, // There is no way to write synchronous elegant, and finally also asynchronous way to write the result of the layer of callback. function readFile(path) { return new Promise((res, rej) => { fs.readFile(path, 'utf-8', (err, data) => { if(err) { rej(err); }else { res(data); }}})}); readFile('https://api.github.com/users/superman66') .then((val) => { return readFile(val); }, () => {}).then((val) => { return readFile(val); }) .then((val) => { console.log(val); }); // async async function read(url) {let val1 = await readFile(url); let val2 = await readFile(val1); let val3 = await readFile(val2); } read('https://api.github.com/users/superman66') .then((val) => console.log(val));Copy the code
      • Solve the problem that try catch can catch exceptions asynchronously
        async function read(url) {
            try {
                let val1 = await readFile(url);
                let val2 = await readFile(val1);
                let val3 = await readFile(val2);
            }catch(e) {
                console.log(e);
            }
        }
        readFile('./data/number.txt').then((val) => console.log(val));
        Copy the code
      • Resolve synchronous concurrent asynchronous results
        • Promise.all()
          Promise.all() is used to pass multiple Promise objects when used. // Second, it succeeds only when all of them succeed. All ([readFile('./data/number1.txt '), readFile('./readFile/number2.txt'), readFile('./data/number3.txt')]) .then((val) => console.log(val), (reason) => console.log(reason));Copy the code
        • async
          async function read1() { let val1 = null; try{ val1 = await readFile('./data/number1.txt'); console.log(val1); }catch(e) { console.log(e); } } async function read2() { let val2 = null; try{ val2 = await readFile('./data/number2.txt'); console.log(val2); }catch(e) { console.log(e); } } async function read3() { let val3 = null; try { val3 = await readFile('./data/number3.txt'); console.log(val3); }catch(e) { console.log(e); } } function readAll(... args) { args.forEach((ele) => { ele(); }) } readAll(read1, read2, read3);Copy the code
  • The ultimate state of asynchronous programming is that you don’t care if it’s asynchronous at all. In short, async functions are syntactic sugar for Generator functions.
  • Advantages:
    • Built-in actuator
      • The execution of Genarator function must depend on the executor, so there is Co function library, while async function has its own executor, that is to say, the execution of async function is exactly the same as ordinary functions, as long as one line.
    • Better semantics
      • Async and await are clearer than asterisks and yield semantics. Async means that an asynchronous operation is taking place in a function, and async means that the following expression needs to wait for the result.
    • Wider adaptability
      • According to the co library convention, yield can only be followed by Thunk or Promise, while async can be followed by await with Promise and primitive values (numeric, string, Boolean but equivalent to synchronous operation).
    • The return value is Promise
      • Async functions return Promise objects, which are more convenient than iterators returned by Generator functions and can be called directly using the then() method.
  • Async functions are so new that they are not in ES6, but in ES7. At present, it is still in the proposal stage, but the transcoders Babel and ReGenerator are already supported and can be used after transcoding.
  • Pay attention to the point
    • Await the Promise object after the await command, and the result may be rejected, so it is better to await the await command in the try… In the catch block.
    • ‘await’ can only be used in async functions. If we use ‘await’ in normal functions, we will get an error. The above code will get an error because ‘await’ is used in normal functions. The above code may not work because the three db.post operations will be executed concurrently, that is, at the same time, rather than second. the correct way to write this is with a for loop
    • If you really want multiple requests to execute concurrently, you can use the promise.all method.

Rest parameters

  • Objective:
    • The Rest argument is used to get the extra arguments to the function, forming an array at the end of the parameter so that the arguments object is not needed.
    • Mainly used to handle indefinite parameters
    funtion fn(a, b, ... args) {// ...
    }
    Copy the code
  • Rest arguments differ from arguments objects:
    • Rest arguments only include arguments that are not given names; arguments include all arguments.
    • Arguments objects are not real arrays, while rest arguments are array instances that can be applied directly to methods like sort, map, etc
    • Arguments objects have some extra functionality of their own (like Callee)
    • Rest arguments simplify the use of arguments to get extra arguments
  • Note:
    • The rest parameter cannot be followed by any other parameter; otherwise, an error will be reported.
    • The length property of the function, excluding the REST argument
    • Rest parameters can be structured (more informally, parsed the Rest parameter data into a one-to-one mapping), and don’t forget to enclose the parameter in [], because it is an array.
      function fn(... [a, b, c]) { console.log(a + b + c); } fn(1);
      fn(1.2.3);
      fn(1.2.3.4);
      Copy the code

Iterator

  • Purpose: ES6 introduces this Iterator for the data to have uniform traversal or for… Array.from and so on, so that we can write code without extensive refactoring.
  • define
    • The idea of Iterator comes from our iterative model
    • ForEach iterates over arrays, for in iterates over objects, $. Each iterates over arrays and objects, and Iterator iterates over sets and maps.
    • Set and Map both have symbols.Iterator ports, which can be used for… Of the iteration
      // Turn non-iterable data into iterable data
      let obj = {
          0: 'a'.1: 'b'.2: 'c',
          length: 3,
          [Symbol.iterator]: function() {
              let curIndex = 0;
              let next = () => {
                  return {
                      value: this[curIndex],
                      done: this.length == ++ curIndex
                  }
              }
              return {
                  next
              }
          }
      }
      console.log([...obj])
      for(let p of obj) {
          console.log(p);
      }
      Copy the code
    • The Generator generates an iterator from symbol. iterator.
  • classification
    • Inner iterator
      • Array.prototype.forEach is what we call an iterator. It is a function made with the idea of iteration mode.
    • External iterator
      • Code implementation (ES5 implementation)
        function OuterInterator() {
            let curIndex = 0;
            let next = () => {
                return{ value: o[curIndex], done: o.length == ++ curIndex; }}return {
                next
            }
        }
        let oIt = OuterIterator(arr);
        Copy the code

Symbol

  • The characteristics of
    • uniqueness
    • Iterator arr, Set, Map, arguments, nodelist all have this property Symbol. Iterator this property equals the iterator function

Loading JavaScript asynchronously

  • Disadvantages of JS loading: the loading tool method does not need to block the document, too much JS loading will affect the page efficiency, once the network speed is not good, then the whole site will wait for JS loading without subsequent rendering work
  • Purpose: Some tools and methods need to be loaded on demand.
  • Three scenarios for asynchronous loading of JavaScript
    • Defere asynchronous loading
      • But it will not be executed until the DOM document is fully parsed, and only IE can use it. (Execute without blocking page load) (Support IE)
    • Async Load asynchronously
      • Async can only load external scripts and cannot write JS inside script tags.
    • Create the script, insert it into the DOM, and load the callBack
      • Code implementation
        function loadScript(url, callback) { var script = document.createElement('script'), script.type = 'text/javaScript'; if(script.readyState) { // IE if(script.onreadystatechange === 'complete' || script.onreadystatechange === 'loaded') { callback(); }}else {// FireFox, Safari, Chrome and Opera script.onload = function() {callback(); } } script.url = url; document.head.appendChild(script); }Copy the code

Loading the CSS asynchronously

  • Load CSS code asynchronously by dynamically inserting link tags with JS
    var myLink = document.createElement('link');
    myLink.rel = 'stylesheet';
    'myLink.href = './index.css';
    documemt.head.insertBefore(myLink, document.head.childNodes[document.head.childNodes.length - 1].nextSibling);
    Copy the code
  • Use the media property on link
    • Set it to a value that does not match the user’s current browser environment, such as media=”print”, or even a completely invalid value such as media=”jscourse”.
    • This way, the browser will assume that the CSS file is of very low priority and will load it without blocking. However, in order to disable CSS rules, the media value must be changed correctly.
      <link rel="style" href="css.style" media="jscourse" onload="this.media='all'">
      Copy the code
  • rel=”preload”
    • The preload attribute tells the browser that the resource will be used later, so load it ahead of time. So when you see that it’s loaded, you still have to change the rel back in order for the CSS to work.
    • The semantics are better
    • As =”style”, so preload can be used not only for CSS files, but for most resource files. Like a JS file
      <link rel="preload" href="sccriptfile.js" as="script"> Var oScript = document.createElement('script'); var oScript = document.createElement('script'); script.src = 'index.js'; document.body.appendChild(script);Copy the code
    • Chrome supports it perfectly, but not the rest.

Reference link: www.cnblogs.com/cjx-work/p/… Juejin. Cn/post / 684490…