寫給小白看的 JavaScript 非同步

来源:http://www.cnblogs.com/gongyue/archive/2017/11/26/7899111.html
-Advertisement-
Play Games

某天突然寫了個方法要從後臺調用數據,顯示在前臺頁面,但是輸出結果總是空 undefined,得不到數據。多方找資料才發現,原來是入了 JS 非同步的 “坑”。 我們常常聽到單線程、多線程、同步、非同步這些概念,那麼這些東西到底是什麼呢? 那麼我們先從上面那幾個概念說起 o( ̄▽ ̄) ブ 單線程、多線程、 ...


某天突然寫了個方法要從後臺調用數據,顯示在前臺頁面,但是輸出結果總是空 undefined,得不到數據。多方找資料才發現,原來是入了 JS 非同步的 “坑”。

我們常常聽到單線程、多線程、同步、非同步這些概念,那麼這些東西到底是什麼呢? 那麼我們先從上面那幾個概念說起 o( ̄▽ ̄) ブ

單線程、多線程、同步、非同步基本理解

每個正在運行的程式(即進程)至少有一個線程,被稱為主線程。主線程在啟動程式時被創建,用於執行 main 函數。

  • 單線程就是只有一個主線的線程,代碼從上往下順序運行,主線程負責執行程式的所有代碼(UI 展現以及刷新,網路請求,本地存儲等等)【一個線程要做所有的事情,想想都有點累呢】

  • 多線程顧名思義,就是有多個線程的程式,可以由用戶自主創建。用戶自主創建的若幹進程相對於主線程而言就是子線程。子線程和主線程都是獨立的運行單元,各自的執行互不影響,因此能夠併發執行。

光聽這些乾巴巴的理論是不是覺得有點暈? 巧了,我乍一看的時候也暈。 在找資料的過程中,我發現了別人的這麼一個形象的比喻。

打個比方,單線程就是你去廚房又燒飯又燒菜,一個人來回跑;多線程就是兩個人,一個單做飯,一個單做菜。

這麼說,應該更好理解了吧?

而什麼又是同步和非同步呢?

我們用一個簡單的生活例子來說明。

你打電話訂酒店,問工作人員有沒有房間,這時候,工作人員需要查找有沒有房間才能回答你。

  • 同步就是不掛電話一直等,直到工作人員告訴你有沒有房間。

  • 非同步就是掛斷電話,你去做別的事情,比如吃飯喝水,工作人員查到了信息再打電話告訴你。

那麼我們的主題來了

JS 的非同步操作是怎樣的呢?

JS 的執行環境是單線程的,也就是說,程式順序執行下來,一次只能執行一個任務,程式想要往下運行,就必須等待當前的任務執行完畢,不管當前的任務要執行多久(要是後面的程式急著跑出來可真的是等的很難受呢)。

為瞭解決後面程式等的難受的這個阻塞問題。JavaScript 有一種非同步處理模式,其實就是延時處理。

我們再來拋出例子來說明。

 var getUserInfo = function () {

           $.getJSON("http://www.easy-mock.com/mock/5a09868228b23066479b8379/ajaxData/getUserInfo", function () {

               return data;

           });

       }

       var data = getUserInfo();

       renderUserInfo(data)

web前端/H5/javascript學習群:250777811

歡迎關註此公眾號→【web前端EDU】跟大佬一起學前端!歡迎大家留言討論一起轉發

getUserInfo 這個函數被調用,要取後臺取數據,可能要耗費很多時間,這就要讓 renderUserInfo 一直等著,直到取出 data 才能運行。幸好 JS 有非同步操作,取數據的時候,不用 renderUserInfo 一直等著 data 取出來,而是直接執行。

這麼說的話,那麼這兩個函數到底是什麼順序執行的吶?不急,我們來調試一下:

var getUserInfo = function () {

           console.log('aaa');

           $.getJSON("http://www.easy-mock.com/mock/5a09868228b23066479b8379/ajaxData/getUserInfo", function () {

               console.log('bbb');

               return data;

           });

       }

       var data = getUserInfo();

       console.log(data);

       console.log('ccc');

       renderUserInfo(data);

 

順序執行下來的輸出原以為是 "aaa","bbb","ccc" 吧?

然而事情並沒有這麼簡單。我們來看一下控制台的輸出:

 

輸出的結果竟然不是順序的。 也就是說函數執行到 getJSON 取數據的時候,程式並沒有等它取出數據再執行下一步,而是跳過了取數據這一個階段,直接執行輸出 data 了,因此,data 也為空。

這就是 JS 的非同步機制了。

 

web前端/H5/javascript學習群:250777811

歡迎關註此公眾號→【web前端EDU】跟大佬一起學前端!歡迎大家留言討論一起轉發


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • Function()是頂級的構造器 Object.prototype是頂級的原型對象 函數有prototype屬性,對象有__proto__欄位 ,而這個欄位的值,等於此對象的構造器(函數)的原型對象(prototype) js中一切都是對象,都有構造器(constructor) ...
  • Javascript OOP 創建對象: 構造型函數方式: 1、可以創建很多個對象 2、函數裡面是可以寫代碼的 對象字面量形式: Object 實例方法: 1、prototype的方式 2、其它 靜態方法: 成員的訪問: js的2大特性: 1、弱類型 2、動態性 instanceof: 構造器(Co ...
  • 錯誤描述 當form表單加FormGroup屬性時報錯 Can't bind to 'formGroup' since it isn't a known property of 'form' 原因分析與解決方案 在使用form表單時,如果用到了form-group與formControlName,需 ...
  • 隨機生成10個0~100不重覆的數字(包含0和100); 需要用到的知識點:隨機數 去重 下麵放代碼 寫代碼前思路一定要清晰,整理好邏輯再寫會讓你的開發事半功倍! ...
  • HTML5 作為下一代網站開發技術,無論你是一個 Web 開發人員或者想探索新的平臺的游戲開發者,都值得去研究。藉助尖端功能,技術和 API,HTML5 允許你創建響應性、創新性、互動性以及令人驚嘆的漂亮網站。更進一步,你也可以使用 HTML5 創建原來只能用於桌面平臺上的複雜應用程式。 這篇文章挑 ...
  • 最近在學習vue,今天看到自定義事件的表單輸入組件,糾結了一會會然後恍然大悟...官方教程寫得不是很詳細,所以我決定總結一下。 v-model語法糖 v-model實現了表單輸入的雙向綁定,我們一般是這麼寫的: 通過該語句實現price變數與輸入值雙向綁定 實際上v-model只是一個語法糖,真正的 ...
  • 之前有寫過css/css3實現元素的水平和垂直居中的幾種方法點我,但是css3屬性不是所有瀏覽器都能相容的,今天寫下js實現未知寬高的元素的水平和垂直居中。 如果需要在有滾動條的情況的下要實現居中的效果,則需要加上scrollTop和scrollLeft。 ...
  • 這兩天做了一個全選反選的案例,用了幾種方法,剛開始寫的磕磕絆絆,聽老師講解後理清思路,再來寫就很容易了。其實還是寫代碼時候的思路問題。首先要分析功能,然後分步實現,不要攪在一起。下麵幾種方法為比較精簡的方法,用到classList屬性,剛開始寫的兩個方法都比較原始,所以相對比較複雜,就不放上來了。 ...
一周排行
    -Advertisement-
    Play Games
  • 前言 本文介紹一款使用 C# 與 WPF 開發的音頻播放器,其界面簡潔大方,操作體驗流暢。該播放器支持多種音頻格式(如 MP4、WMA、OGG、FLAC 等),並具備標記、實時歌詞顯示等功能。 另外,還支持換膚及多語言(中英文)切換。核心音頻處理採用 FFmpeg 組件,獲得了廣泛認可,目前 Git ...
  • OAuth2.0授權驗證-gitee授權碼模式 本文主要介紹如何筆者自己是如何使用gitee提供的OAuth2.0協議完成授權驗證並登錄到自己的系統,完整模式如圖 1、創建應用 打開gitee個人中心->第三方應用->創建應用 創建應用後在我的應用界面,查看已創建應用的Client ID和Clien ...
  • 解決了這個問題:《winForm下,fastReport.net 從.net framework 升級到.net5遇到的錯誤“Operation is not supported on this platform.”》 本文內容轉載自:https://www.fcnsoft.com/Home/Sho ...
  • 國內文章 WPF 從裸 Win 32 的 WM_Pointer 消息獲取觸摸點繪製筆跡 https://www.cnblogs.com/lindexi/p/18390983 本文將告訴大家如何在 WPF 裡面,接收裸 Win 32 的 WM_Pointer 消息,從消息裡面獲取觸摸點信息,使用觸摸點 ...
  • 前言 給大家推薦一個專為新零售快消行業打造了一套高效的進銷存管理系統。 系統不僅具備強大的庫存管理功能,還集成了高性能的輕量級 POS 解決方案,確保頁面載入速度極快,提供良好的用戶體驗。 項目介紹 Dorisoy.POS 是一款基於 .NET 7 和 Angular 4 開發的新零售快消進銷存管理 ...
  • ABP CLI常用的代碼分享 一、確保環境配置正確 安裝.NET CLI: ABP CLI是基於.NET Core或.NET 5/6/7等更高版本構建的,因此首先需要在你的開發環境中安裝.NET CLI。這可以通過訪問Microsoft官網下載並安裝相應版本的.NET SDK來實現。 安裝ABP ...
  • 問題 問題是這樣的:第三方的webapi,需要先調用登陸介面獲取Cookie,訪問其它介面時攜帶Cookie信息。 但使用HttpClient類調用登陸介面,返回的Headers中沒有找到Cookie信息。 分析 首先,使用Postman測試該登陸介面,正常返回Cookie信息,說明是HttpCli ...
  • 國內文章 關於.NET在中國為什麼工資低的分析 https://www.cnblogs.com/thinkingmore/p/18406244 .NET在中國開發者的薪資偏低,主要因市場需求、技術棧選擇和企業文化等因素所致。歷史上,.NET曾因微軟的閉源策略發展受限,儘管後來推出了跨平臺的.NET ...
  • 在WPF開發應用中,動畫不僅可以引起用戶的註意與興趣,而且還使軟體更加便於使用。前面幾篇文章講解了畫筆(Brush),形狀(Shape),幾何圖形(Geometry),變換(Transform)等相關內容,今天繼續講解動畫相關內容和知識點,僅供學習分享使用,如有不足之處,還請指正。 ...
  • 什麼是委托? 委托可以說是把一個方法代入另一個方法執行,相當於指向函數的指針;事件就相當於保存委托的數組; 1.實例化委托的方式: 方式1:通過new創建實例: public delegate void ShowDelegate(); 或者 public delegate string ShowDe ...