首页 >web前端 >js教程 >了解异步 JS

了解异步 JS

王林
王林原创
2024-09-01 21:07:111026浏览

Understanding Async JS

Async JS 的目标:处理在后台运行的长时间运行的任务

  • 用例:通过 AJAX 调用从远程服务器获取数据。
  • 例如。设置图像源、定时器、Promises、Fetch API、Async-Await、Geolocation API、Error-Handling。

同步代码:

  • 按顺序逐行执行,其中由作为执行上下文一部分的执行线程写入。
  • Dis:当一行代码需要很长时间才能执行,例如 AJAX 调用、D/b 访问、警报窗口等,这会阻塞代码执行直到完成。

异步代码

  • 计时器在后台运行,不会阻塞代码,即不会阻塞执行的主线程。
  • 后台运行的任务完成后执行异步代码。
  • 执行不会等待异步任务完成其工作。
  • 异步 - 不同时发生。
  • 回调不会使代码自动异步。前任。数组映射方法接受回调,但它不会使代码异步。只有某些函数(例如计时器)以异步方式工作,但并非所有回调。
const p = document.querySelector('.p');
setTimeout(function(){
  p.textContent = "Welcome to JS";
}, 3000); // C/b executes after duration.
p.style.color = 'red';
Ex. Setting source of an img is an async operation, while rest of the code is running. Once the image is loaded completely, a load event will be emitted by JS for which we can listen.

const img = document.querySelector('.cat');
img.src = 'cat.jpg'
img.addEventListener('load',function(){
  img.classList('fadeIn');
});
p.style.width = '300px';
  • 单独的事件监听器不会使代码异步。例如,按钮单击侦听器不在后台执行任何工作。因此,不涉及异步行为。

阿贾克斯

  • 允许我们以异步方式与远程 Web 服务器通信。
  • 使用 AJAX 调用动态地从 Web 服务器请求数据。

应用程序编程接口

  • 另一个软件使用的软件,可实现黑白应用程序的通信。
  • 例如。 DOM API、Geoloaction API 等都是独立的软件,允许软件与它们交互
  • 我们可以通过使用类并公开一些方法来实现 API。
  • 在线 API:在服务器上运行的应用程序,接收数据请求,并发送回数据作为响应。
  • API 是使用后端开发构建的或使用其他开发人员免费向我们提供的第 3 方 API。
  • 例如。几乎所有内容都有示例 API。
  • 之前使用的是 XML,现在只使用 JSON,即 JS 对象转换为字符串。
# First API Call: Older way of doing AJAX using XHR. Modern way uses fetch API.
- CORS need to be Yes/Unknown to access 3rd party APIs from our code.
- AJAX call is done in the background, while the rest of the code keeps running which makes it non-blocking.
- Hence, register a callback for the load event on request object.
- Request is sent in the background, when its complete 'load' event will be fired. As soon data arrives, Callback fn will be called.

HTML:
<main class="container">
  <div class="countries">
</div>
</main>

JS:
const getCountryData = function(country){
const btn = document.querySelector('.btn-country');
const countriesContainer = document.querySelector('.countries');

// 1. request created
const request = new XMLHttpRequest(); 
// 2.request opened
request.open("GET", `https://restcountries.com/v3.1/name/${country}`); 
// 3. request sent
request.send();

// 4. When data arrives, load event will be fired & below C/b will be invoked.
// 5. response arrives in the property responseText of request object in JSON i.e big string of text will be received from AJAX call which needs to be converted to JS object.
// 6. Convert JSON to JS.
request.addEventListener("load", function () {
  // console.log(this);    this refers to request object here. 'this' can be replaced with request object.
  // console.log(this.responseText);  will only be set when data has arrived.

  // Both lines yield same result below.
  //const [ data ] = JSON.parse(this.responseText);
  const data = JSON.parse(this.responseText)[0];
  console.log(data);

  const html = `<article class="country">
  <img src=${data.flags.svg} alt="" class="country__img">
  <div class="country__data">
    <h3 class="country__name">${data.name.common}</h3>
    <h4 class="country__region">${data.region}</h4>
    <p class="country__row"><span>${(+data.population / 1000000).toFixed(1)}</span> mn</p>
    <p class="country__row"><span>${data.languages[Object.keys(data.languages)[0]]}</span></p>
    <p class="country__row"><span>${data.currencies[Object.keys(data.currencies)[0]].name}</span></p>
  </div>
</article>`;
  countriesContainer.insertAdjacentHTML('beforeend', html);
  countriesContainer.style.opacity = 1;
});
};

// All AJAX calls are happening in parallel
getCountryData('usa');
getCountryData('russia');
getCountryData('germany');
getCountryData('brazil');
getCountryData('india');

回调地狱:

  • 链接 AJAX 请求将使它们按顺序工作,即第一个请求完成后将生成第二个请求。

- 由于为需要按顺序进行的嵌套 AJAX 调用定义的嵌套回调而导致。

// This below triangular shape denotes callback hell. Makes code hard to maintain.
// GPP: Code which is hard to understand is bad code, hence difficult to add features
// Promises help us to resolve this Callback Hell problem.

setTimeout(() => {
  console.log("1 sec passed");
  setTimeout(() => {
    console.log("2 sec passed");
    setTimeout(() => {
      console.log("3 sec passed");
      setTimeout(() => {
        console.log("4 sec passed");
        setTimeout(() => {
          console.log("5 sec passed");
          }, 1000);
        }, 1000);
      }, 1000);
    }, 1000); 
}, 1000);



// Get the neighbouring countries
const renderCountry = function (data) {
  const btn = document.querySelector(".btn-country");
  const countriesContainer = document.querySelector(".countries");

  const html = `<article class="country">
  <img src=${data.flags.svg} alt="" class="country__img">
  <div class="country__data">
    <h3 class="country__name">${data.name.common}</h3>
    <h4 class="country__region">${data.region}</h4>
    <p class="country__row"><span>${(+data.population / 1000000).toFixed(
      1
    )}</span> mn</p>
    <p class="country__row"><span>${
      data.languages[Object.keys(data.languages)[0]]
    }</span></p>
    <p class="country__row"><span>${
      data.currencies[Object.keys(data.currencies)[0]].name
    }</span></p>
  </div>
</article>`;
  countriesContainer.insertAdjacentHTML("beforeend", html);
  countriesContainer.style.opacity = 1;
};

const getNeighbours = function (country) {
  const request = new XMLHttpRequest();
  request.open("GET", `https://restcountries.com/v3.1/name/${country}`);
  request.send();

  request.addEventListener("load", function () {
    const [data] = JSON.parse(this.responseText);
    console.log(data);
    renderCountry(data);

    const [neightbour] = data.borders;
    if(!neightbour) return;

    // request2 is Dependent on request1 as its invoke after request1. request2 will its own event listener.
    const request2 = new XMLHttpRequest();
    request2.open("GET", `https://restcountries.com/v3.1/alpha/${data.borders}`);
    request2.send();

    request2.addEventListener("load", function () {
    const [data2] = JSON.parse(this.responseText);
    console.log(data2);
    renderCountry(data2);
  });
};

getNeighbours("italy");

以上是了解异步 JS的详细内容。更多信息请关注PHP中文网其他相关文章!

声明:
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn